diff options
Diffstat (limited to 'src/main.c')
-rw-r--r-- | src/main.c | 139 |
1 files changed, 9 insertions, 130 deletions
@@ -6,133 +6,11 @@ #include <errno.h> #include <string.h> +#include <map.h> +#include <parse.h> #include <log.h> -#include <hash.h> -#include <hashmap.h> - -struct hashmap *all_terms; - -typedef enum { INV, ABS, APP, VAR } term_type_t; - -struct term { - term_type_t type; - hash_t hash; - size_t refs; - union { - struct { - hash_t term; - } abs; - struct { - hash_t lhs; - hash_t rhs; - } app; - struct { - int index; - } var; - } u; -}; - -static void deref_term(struct term *term) -{ - if (term->type == ABS) { - deref_term(hashmap_get(all_terms, term->u.abs.term)); - } else if (term->type == APP) { - deref_term(hashmap_get(all_terms, term->u.app.lhs)); - deref_term(hashmap_get(all_terms, term->u.app.rhs)); - } - - // TODO: remove from hashmap? - if (--term->refs == 0) - free(term); -} - -static void hashmap_free_term(void *item) -{ - struct term *term = *(struct term **)item; - free(term); -} - -static struct term *new_term(term_type_t type) -{ - struct term *term = malloc(sizeof(*term)); - if (!term) - fatal("out of memory!\n"); - term->type = type; - return term; -} - -// TODO: bit rec_bblc -static hash_t rec_blc(char **term) -{ - hash_t res = 0; - struct term *res_term = 0; - term_type_t res_type = 0; - - if (!**term) { - fatal("invalid parsing state!\n"); - } else if (**term == '0' && *(*term + 1) == '0') { - (*term) += 2; - res_type = ABS; - hash_t inner_hash = rec_blc(term); - res = hash((uint8_t *)&res_type, sizeof(res_type), inner_hash); - - struct term **handle = hashmap_get(all_terms, res); - if (handle) { - res_term = *handle; - res_term->refs++; - } else { - res_term = new_term(ABS); - res_term->refs = 1; - res_term->hash = res; - res_term->u.abs.term = inner_hash; - hashmap_set(all_terms, &res_term, res); - } - } else if (**term == '0' && *(*term + 1) == '1') { - (*term) += 2; - res_type = APP; - hash_t lhs_hash = rec_blc(term); - hash_t rhs_hash = rec_blc(term); - res = hash((uint8_t *)&res_type, sizeof(res_type), lhs_hash); - res = hash((uint8_t *)&res, sizeof(res), rhs_hash); - - struct term **handle = hashmap_get(all_terms, res); - if (handle) { - res_term = *handle; - res_term->refs++; - } else { - res_term = new_term(res_type); - res_term->refs = 1; - res_term->hash = res; - res_term->u.app.lhs = lhs_hash; - res_term->u.app.rhs = rhs_hash; - hashmap_set(all_terms, &res_term, res); - } - } else if (**term == '1') { - res_type = VAR; - const char *cur = *term; - while (**term == '1') - (*term)++; - int index = *term - cur - 1; - res = hash((uint8_t *)&res_type, sizeof(res_type), index); - - struct term **handle = hashmap_get(all_terms, res); - if (handle) { - res_term = *handle; - res_term->refs++; - } else { - res_term = new_term(res_type); - res_term->refs = 1; - res_term->hash = res; - res_term->u.var.index = index; - hashmap_set(all_terms, &res_term, res); - } - (*term)++; - } else { - (*term)++; - res = rec_blc(term); - } - return res; -} +#include <lib/hash.h> +#include <lib/hashmap.h> static char *read_file(FILE *f) { @@ -169,14 +47,15 @@ int main(int argc, char *argv[]) { debug_enable(1); if (argc != 2) - fatal("usage: %s <file>\n", argv[0]); + fatal("usage: %s <file>\n", argc ? argv[0] : "calm"); char *term = read_path(argv[1]); + map_initialize(); + char *orig_term = term; - all_terms = hashmap_new(sizeof(struct term *), 0, hashmap_free_term); - rec_blc(&term); + parse_blc(&term); free(orig_term); - hashmap_free(all_terms); + map_destroy(); return 0; } |