diff options
| author | Danny van Kooten <dannyvankooten@users.noreply.github.com> | 2020-03-18 19:21:48 +0100 | 
|---|---|---|
| committer | Danny van Kooten <dannyvankooten@users.noreply.github.com> | 2020-03-18 19:21:48 +0100 | 
| commit | 8d74fd5b0e5fc9f319a5b7d2e0716afcc312fd75 (patch) | |
| tree | a6c195d183694304fbe238a68486aceea01d404a | |
| parent | 82de777afb99aa4129abcb01da76bf62e7b45263 (diff) | |
| download | unja-8d74fd5b0e5fc9f319a5b7d2e0716afcc312fd75.tar.gz unja-8d74fd5b0e5fc9f319a5b7d2e0716afcc312fd75.zip  | |
clean-up environment in env_free(). add hashmap_walk function for visiting all values in a hashmap.
| -rw-r--r-- | src/hashmap.c | 16 | ||||
| -rw-r--r-- | src/hashmap.h | 3 | ||||
| -rw-r--r-- | src/parser.c | 94 | ||||
| -rw-r--r-- | src/template.c | 21 | ||||
| -rw-r--r-- | tests/test_template.c | 7 | 
5 files changed, 38 insertions, 103 deletions
diff --git a/src/hashmap.c b/src/hashmap.c index f99ba4c..600a005 100644 --- a/src/hashmap.c +++ b/src/hashmap.c @@ -51,7 +51,7 @@ void *hashmap_get(struct hashmap *hm, char *key) {      int pos = HASH(key);      struct node *node = hm->buckets[pos];      while (node) { -        if (strcmp(node->key, key) == 0) { +        if (node->key && strcmp(node->key, key) == 0) {              return node->value;          } @@ -112,6 +112,20 @@ void *hashmap_remove(struct hashmap *hm, char *key) {      return NULL;  } +void hashmap_walk(struct hashmap *hm, void (*fn)(void *value)) { +    struct node *node; +    struct node *next; + +    for (int i=0; i < HASHMAP_CAP; i++) { +        node = hm->buckets[i]; +        while (node) { +            next = node->next; +            fn(node->value); +            node = next; +        } +    } +} +  /* free hashmap related memory */  void hashmap_free(struct hashmap *hm) {      struct node *node; diff --git a/src/hashmap.h b/src/hashmap.h index be2b80e..dbb45da 100644 --- a/src/hashmap.h +++ b/src/hashmap.h @@ -9,4 +9,5 @@ void *hashmap_insert(struct hashmap *hm, char *key, void *value);  void *hashmap_get(struct hashmap *hm, char *key);  void *hashmap_resolve(struct hashmap *hm, char *key);  void *hashmap_remove(struct hashmap *hm, char *key); -void hashmap_free(struct hashmap *hm);
\ No newline at end of file +void hashmap_free(struct hashmap *hm); +void hashmap_walk(struct hashmap *hm, void (*fn)(void *value));
\ No newline at end of file diff --git a/src/parser.c b/src/parser.c deleted file mode 100644 index e61b1e5..0000000 --- a/src/parser.c +++ /dev/null @@ -1,94 +0,0 @@ - -#include <stdlib.h> -#include <string.h> - -struct text { -    char *str; -}; - -struct symbol { -    char *value; -}; - -struct expression { -    struct symbol symbol; -}; - -struct statement { - -}; - -/* discard during parsing phase */ -struct comment {}; - - -enum node_type { -    NODE_EXPR, -    NODE_COMMENT, -    NODE_TEXT, -}; - -struct node { -    enum node_type type; -    union content { -        struct expression expr; -        struct comment comment; -        struct text text; -    } content; -}; - -struct ast { -    int size; -    int cap; -    struct node **nodes; -}; - -enum token_type { -    TOK_EOF, -    TOK_EXPR_OPEN, -    TOK_EXPR_CLOSE, -    TOK_COMMENT_OPEN, -    TOK_COMMENT_CLOSE, -    TOK_STMT_OPEN, -    TOK_STMT_CLOSE, -    TOK_MINUS, -    TOK_SYMBOL, -    TOK_TEXT, -}; - -struct token { -    enum token_type type; -    char *literal; -}; - -struct token gettoken(char *str) { -    struct token t; -    switch (str[0]) { -        case '{': - -        break; - -        case '}': - -        break; - -        case '\0':  -            t.type = TOK_EOF; -        break; -    } - -    return t; -}; - -struct ast* parse(char *str) { -    struct ast* ast = malloc(sizeof *ast); -    ast->size = 0; -    ast->cap = 64; -    ast->nodes = malloc(ast->cap * sizeof *ast->nodes); - -    for (struct token t = gettoken(str); t.type != TOK_EOF; t= gettoken(str)) { - -    } - -    return ast; -}
\ No newline at end of file diff --git a/src/template.c b/src/template.c index 7ea4d05..a1b3ef4 100644 --- a/src/template.c +++ b/src/template.c @@ -3,6 +3,7 @@  #include <err.h>  #include <unistd.h>  #include <dirent.h> +#include <string.h>  #include "vendor/mpc.h"  #include "template.h" @@ -167,9 +168,13 @@ struct env *env_new(char *dirname) {              continue;          } -        char *name = de->d_name; +        // copy template name as closedir free's it otherwise +        char *name = malloc(strlen(de->d_name) + 1); +        strcpy(name, de->d_name); +          char *tmpl = read_file(name);          mpc_ast_t *ast = parse(tmpl); +        free(tmpl);          struct template *t = malloc(sizeof *t);          t->ast = ast; @@ -182,14 +187,24 @@ struct env *env_new(char *dirname) {          }          hashmap_insert(env->templates, name, t); +              }      closedir(dr);           return env;  } +void template_free(void *v) { +    struct template *t = (struct template *)v; +    hashmap_free(t->blocks); +    mpc_ast_delete(t->ast); +    free(t->name); +    free(t); +} +  void env_free(struct env *env) { -    // TODO: Free template strings +    hashmap_walk(env->templates, template_free); +    hashmap_free(env->templates);      free(env);  } @@ -215,7 +230,7 @@ char *read_file(char *filename) {  }  char *trim_trailing_whitespace(char *str) { -    for (int i=strlen(str)-1; isspace(str[i]); i--) { +    for (int i=strlen(str)-1; i >= 0 && isspace(str[i]); i--) {          str[i] = '\0';      }      return str; diff --git a/tests/test_template.c b/tests/test_template.c index 34022fa..b427f7c 100644 --- a/tests/test_template.c +++ b/tests/test_template.c @@ -182,14 +182,13 @@ TEST(for_block_whitespace) {  TEST(var_dot_notation) {      char *input = "Hello {{user.name}}!"; -     struct hashmap *user = hashmap_new(); -    hashmap_insert(user, "name", "Danny"); -      struct hashmap *ctx = hashmap_new(); +    struct hashmap *user = hashmap_new(); +    hashmap_insert(user, "name", "Danny");      hashmap_insert(ctx, "user", user); -          char *output = template_string(input, ctx);      assert_str(output, "Hello Danny!"); +    hashmap_free(user);      hashmap_free(ctx);      free(output);  }  | 
