diff options
Diffstat (limited to 'compiler/lexer/keywords.c')
-rw-r--r-- | compiler/lexer/keywords.c | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/compiler/lexer/keywords.c b/compiler/lexer/keywords.c new file mode 100644 index 0000000..0e95048 --- /dev/null +++ b/compiler/lexer/keywords.c @@ -0,0 +1,73 @@ +/* + * Keyword hashmap. + * Copyright (c) 2023-2024, Quinn Stephens and the OSMORA team. + * Provided under the BSD 3-Clause license. + */ + +#include <stdbool.h> +#include <stdlib.h> +#include <string.h> +#include "hash.h" +#include "hashmap.h" +#include "debug.h" +#include "lexer/keywords.h" + +#define HASHMAP_ROWS 8 + +struct keyword { + struct hashmap_entry hashmap_entry; + size_t len; + token_kind_t value; +}; + +static bool initialized = false; +static struct list keywords_rows[HASHMAP_ROWS]; +static struct hashmap keywords; + +static void +add_keyword(char *name, token_kind_t value) +{ + size_t len; + struct keyword *kwd; + + len = strlen(name); + kwd = malloc(sizeof(struct keyword)); + kwd->hashmap_entry.hash = hash_data(name, len); + kwd->len = len; + kwd->value = value; + + hashmap_add(&keywords, &kwd->hashmap_entry); +} + +token_kind_t +keywords_find(struct token *tok) +{ + struct keyword *kwd; + + kwd = (struct keyword*)hashmap_find(&keywords, tok->hash); + if (kwd == NULL || kwd->len != tok->len) { + return TK_UNKNOWN; + } + + return kwd->value; +} + +void +keywords_init(void) +{ + if (initialized) { + return; + } + + debug("Initializing keywords...\n"); + + keywords.rows = keywords_rows; + keywords.n_rows = HASHMAP_ROWS; + hashmap_init(&keywords); + + add_keyword("type", TK_TYPE); + add_keyword("enum", TK_ENUM); + add_keyword("struct", TK_STRUCT); + + initialized = true; +} |