summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormetamuffin <metamuffin@disroot.org>2024-06-14 22:14:31 +0200
committermetamuffin <metamuffin@disroot.org>2024-06-14 22:14:31 +0200
commit8a2d1b4928150c361413f4b294e016ee5011a017 (patch)
tree76e1e98f8336f83550592a25e96377df0f0ef044
downloadattocc-8a2d1b4928150c361413f4b294e016ee5011a017.tar
attocc-8a2d1b4928150c361413f4b294e016ee5011a017.tar.bz2
attocc-8a2d1b4928150c361413f4b294e016ee5011a017.tar.zst
a
-rw-r--r--.gitignore1
-rw-r--r--attocc.c134
2 files changed, 135 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..5cc1205
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+/attocc
diff --git a/attocc.c b/attocc.c
new file mode 100644
index 0000000..c18156c
--- /dev/null
+++ b/attocc.c
@@ -0,0 +1,134 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#define NUM_KEYWORDS 32
+static char *KEYWORDS[NUM_KEYWORDS] = {
+ "auto", "break", "case", "char", "const", "continue",
+ "default", "do", "double", "else", "enum", "extern",
+ "float", "for", "goto", "if", "int", "long",
+ "register", "return", "short", "signed", "sizeof", "static",
+ "struct", "switch", "typedef", "union", "unsigned", "void",
+ "volatile", "while"};
+
+enum keyword {
+ kW_AUTO,
+ KW_BREAK,
+ KW_CASE,
+ KW_CHAR,
+ KW_CONST,
+ KW_CONTINUE,
+ KW_DEFAULT,
+ KW_DO,
+ KW_DOUBLE,
+ KW_ELSE,
+ KW_ENUM,
+ KW_EXTERN,
+ KW_FLOAT,
+ KW_FOR,
+ KW_GOTO,
+ KW_IF,
+ KW_INT,
+ KW_LONG,
+ KW_REGISTER,
+ KW_RETURN,
+ KW_SHORT,
+ KW_SIGNED,
+ KW_SIZEOF,
+ KW_STATIC,
+ KW_STRUCT,
+ KW_SWITCH,
+ KW_TYPEDEF,
+ KW_UNION,
+ KW_UNSIGNED,
+ KW_VOID,
+ KW_VOLATILE,
+ KW_WHILE,
+};
+enum operator{
+ OP_ADD,
+ OP_SUB,
+ OP_MUL,
+ OP_DIV,
+ OP_MOD,
+};
+enum token_kind {
+ IDENTIFIER,
+ KEYWORD,
+ CONSTANT,
+ OPERATOR,
+ END,
+};
+union token_data {
+ char *identifier;
+ enum keyword keyword;
+ int constant_value;
+ enum operator operator;
+};
+struct token {
+ enum token_kind kind;
+ union token_data data;
+};
+
+struct token *tokenize(char *source) {
+ char *end = source + strlen(source);
+ char *p = source;
+ int num_tokens = 0;
+ struct token *tokens;
+ while (*p) {
+ int remaining = end - p;
+
+ //* comments
+ if (remaining >= 2) {
+ if (p[0] == '/' && p[1] == '/') {
+ p += 2;
+ while (*p) {
+ if (*p++ == '\n') {
+ break;
+ }
+ }
+ continue;
+ } else if (p[0] == '/' && p[1] == '*') {
+ p += 2;
+ char last = '\0';
+ while (*p) {
+ if (*p == '/' && last == '*') {
+ p++;
+ break;
+ }
+ last = *p;
+ p++;
+ }
+ continue;
+ }
+ }
+
+ //* keyword
+ for (int i = 0; i < NUM_KEYWORDS; i++) {
+ char *kw = KEYWORDS[i];
+ if (remaining >= strlen(kw)) {
+ if (strcmp(kw, p) == 0) {
+ num_tokens += 1;
+
+ tokens = realloc(tokens, sizeof(struct token) * num_tokens);
+ if (!tokens) {
+ fprintf(stderr, "realloc failed");
+ return NULL;
+ }
+ struct token *new_token = &tokens[num_tokens - 1];
+ new_token->kind = KEYWORD;
+ new_token->data.keyword = i;
+
+ p += strlen(kw);
+ continue;
+ }
+ }
+ }
+
+ fprintf(stderr, "unknown token\n");
+ return NULL;
+ }
+ return tokens;
+}
+
+int main() {}