resolve
This commit is contained in:
parent
7d5b4ea151
commit
48587d47de
@ -315,6 +315,8 @@ void ast_decl_visit_body(AstVisitor* v, AstDecl* node)
|
||||
{
|
||||
for (size_t i = 0; i < node->declars_size; ++i)
|
||||
ast_declar_visit(v, node->declars[i]);
|
||||
if (node->function_body)
|
||||
ast_stmt_block_visit(v, node->function_body);
|
||||
}
|
||||
|
||||
void ast_declar_visit(AstVisitor* v, AstDeclar* node)
|
||||
@ -337,7 +339,7 @@ void ast_declar_visit_body(AstVisitor* v, AstDeclar* node)
|
||||
ast_expr_visit(v, node->array.expr);
|
||||
break;
|
||||
case AstDeclar_Function:
|
||||
ast_declar_visit(v, node->pointer.declar);
|
||||
ast_declar_visit(v, node->function.declar);
|
||||
for (size_t i = 0; i < node->function.params_size; ++i)
|
||||
ast_decl_visit(v, node->function.params[i]);
|
||||
break;
|
||||
@ -353,7 +355,6 @@ void ast_expr_visit(AstVisitor* v, AstExpr* node)
|
||||
|
||||
void ast_expr_visit_body(AstVisitor* v, AstExpr* node)
|
||||
{
|
||||
|
||||
switch (node->ty) {
|
||||
case AstExpr_Ident:
|
||||
break;
|
||||
|
||||
21
collection.c
21
collection.c
@ -292,16 +292,6 @@ void keymap_set(Keymap* m, KeymapKey key, void* value)
|
||||
return;
|
||||
}
|
||||
|
||||
printf("index = %ld\n", result.idx);
|
||||
|
||||
if (m->entries_size) {
|
||||
if (keymap_idx(m, result.idx)->key < key) {
|
||||
printf("key is bigger\n");
|
||||
} else {
|
||||
printf("key is smaller\n");
|
||||
}
|
||||
}
|
||||
|
||||
KeymapEntry* entry = m->temp_entry;
|
||||
memset(entry, 0, m->entry_size);
|
||||
|
||||
@ -321,11 +311,10 @@ void keymap_set(Keymap* m, KeymapKey key, void* value)
|
||||
}
|
||||
|
||||
memcpy(keymap_idx(m, result.idx), entry, m->entry_size);
|
||||
|
||||
for (size_t i = 0; i < m->entries_size; ++i) {
|
||||
KeymapEntry* entry = keymap_idx(m, i);
|
||||
printf(" %ld -> %d\n", entry->key, *(int*)entry->value);
|
||||
}
|
||||
}
|
||||
|
||||
void* keymap_get(Keymap* m, KeymapKey key);
|
||||
void* keymap_get(Keymap* m, KeymapKey key)
|
||||
{
|
||||
struct SearchResult result = keymap_search(m, 0, m->entries_size, key);
|
||||
return result.entry ? &result.entry->value : nullptr;
|
||||
}
|
||||
|
||||
13
main.c
13
main.c
@ -89,6 +89,8 @@ int main(int argc, char* argv[])
|
||||
ast_stmt_print(stdout, stmt, 0);
|
||||
|
||||
printf("\n");
|
||||
|
||||
resolver_resolve_top_stmt(resolver, stmt);
|
||||
}
|
||||
|
||||
resolver_free(resolver);
|
||||
@ -100,15 +102,4 @@ int main(int argc, char* argv[])
|
||||
arena_deinit(&ast_arena);
|
||||
arena_deinit(&sym_arena);
|
||||
}
|
||||
|
||||
Keymap map;
|
||||
keymap_init(&map, sizeof(int));
|
||||
|
||||
int a[] = { 3, 1, 4, 1 };
|
||||
keymap_set(&map, 4, &a[3]);
|
||||
keymap_set(&map, 3, &a[2]);
|
||||
keymap_set(&map, 2, &a[1]);
|
||||
keymap_set(&map, 1, &a[0]);
|
||||
|
||||
keymap_deinit(&map);
|
||||
}
|
||||
|
||||
100
resolve.c
100
resolve.c
@ -24,6 +24,8 @@ Syms* syms_new()
|
||||
|
||||
void syms_free(Syms* s)
|
||||
{
|
||||
for (size_t i = 0; i < s->maps_size; ++i)
|
||||
hashmap_deinit(&s->maps[i]);
|
||||
free(s->maps);
|
||||
free(s);
|
||||
}
|
||||
@ -49,9 +51,50 @@ void syms_define(Syms* s, const char* ident, Sym* sym)
|
||||
|
||||
Sym* syms_get(Syms* s, const char* ident)
|
||||
{
|
||||
Hashmap* m = &s->maps[s->maps_size - 1];
|
||||
Sym** res = hashmap_get(m, ident);
|
||||
return res ? *res : nullptr;
|
||||
Sym** res;
|
||||
for (size_t i = 0; i < s->maps_size; ++i)
|
||||
if ((res = hashmap_get(&s->maps[s->maps_size - i - 1], ident)))
|
||||
return *res;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
static void print_sym(Sym* s)
|
||||
{
|
||||
switch (s->ty) {
|
||||
case Sym_Typedef:
|
||||
printf("Typedef");
|
||||
break;
|
||||
case Sym_Declarator:
|
||||
printf("Declarator");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
struct SymPrinter {
|
||||
int depth;
|
||||
};
|
||||
|
||||
static void print_sym_hashmap(void* self, const char* key, void* val)
|
||||
{
|
||||
struct SymPrinter* p = self;
|
||||
Sym* sym = *(Sym**)val;
|
||||
|
||||
printf(" ");
|
||||
for (int i = 0; i < p->depth; ++i)
|
||||
printf(" ");
|
||||
printf("'%s' -> ", key);
|
||||
print_sym(sym);
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
void syms_print(Syms* s)
|
||||
{
|
||||
for (size_t i = 0; i < s->maps_size; ++i) {
|
||||
struct SymPrinter p = {
|
||||
.depth = i,
|
||||
};
|
||||
hashmap_for_each(&s->maps[i], print_sym_hashmap, &p);
|
||||
}
|
||||
}
|
||||
|
||||
typedef enum : unsigned int {
|
||||
@ -65,6 +108,8 @@ struct Resolver {
|
||||
|
||||
Arena* arena;
|
||||
|
||||
Keymap resol_map;
|
||||
|
||||
AstStmt* current_decl_stmt;
|
||||
ResolverFlags flags;
|
||||
};
|
||||
@ -79,14 +124,21 @@ Resolver* resolver_new(Arena* arena)
|
||||
|
||||
.arena = arena,
|
||||
|
||||
.resol_map = { },
|
||||
|
||||
.current_decl_stmt = nullptr,
|
||||
.flags = 0,
|
||||
};
|
||||
|
||||
keymap_init(&r->resol_map, sizeof(Sym*));
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
void resolver_free(Resolver* r)
|
||||
{
|
||||
keymap_deinit(&r->resol_map);
|
||||
|
||||
syms_free(r->ord_syms);
|
||||
syms_free(r->tag_syms);
|
||||
syms_free(r->label_syms);
|
||||
@ -132,6 +184,26 @@ static AstVisitorResult visit_decl(AstVisitor* v, AstDecl* node)
|
||||
return AstVisitor_Break;
|
||||
}
|
||||
|
||||
if (node->function_body) {
|
||||
|
||||
assert(node->declars_size == 1
|
||||
&& node->declars[0]->ty == AstDeclar_Function);
|
||||
|
||||
AstDeclar* d = node->declars[0];
|
||||
|
||||
ast_declar_visit(v, d->function.declar);
|
||||
|
||||
syms_push_scope(r->ord_syms);
|
||||
|
||||
for (size_t i = 0; i < d->function.params_size; ++i)
|
||||
ast_decl_visit(v, d->function.params[i]);
|
||||
|
||||
ast_stmt_block_visit(v, node->function_body);
|
||||
|
||||
syms_pop_scope(r->ord_syms);
|
||||
return AstVisitor_Break;
|
||||
}
|
||||
|
||||
return AstVisitor_Continue;
|
||||
}
|
||||
|
||||
@ -140,9 +212,12 @@ static AstVisitorResult visit_declar(AstVisitor* v, AstDeclar* node)
|
||||
Resolver* r = v->op;
|
||||
|
||||
if (node->ty == AstDeclar_Function) {
|
||||
ast_declar_visit(v, node->function.declar);
|
||||
|
||||
syms_push_scope(r->ord_syms);
|
||||
|
||||
ast_declar_visit_body(v, node);
|
||||
for (size_t i = 0; i < node->function.params_size; ++i)
|
||||
ast_decl_visit(v, node->function.params[i]);
|
||||
|
||||
syms_pop_scope(r->ord_syms);
|
||||
return AstVisitor_Break;
|
||||
@ -170,7 +245,20 @@ static AstVisitorResult visit_expr(AstVisitor* v, AstExpr* node)
|
||||
{
|
||||
Resolver* r = v->op;
|
||||
|
||||
if (node->ty == AstExpr_Ident) { }
|
||||
if (node->ty == AstExpr_Ident) {
|
||||
|
||||
Sym* sym = syms_get(r->ord_syms, node->ident);
|
||||
if (!sym) {
|
||||
fprintf(stderr,
|
||||
"error: use of undeclared '%s' on line %d\n",
|
||||
node->ident,
|
||||
node->loc.line);
|
||||
|
||||
syms_print(r->ord_syms);
|
||||
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
return AstVisitor_Continue;
|
||||
}
|
||||
@ -192,5 +280,5 @@ void resolver_resolve_top_stmt(Resolver* r, AstStmt* stmt)
|
||||
.op = r,
|
||||
};
|
||||
|
||||
visit_stmt(&v, stmt);
|
||||
ast_stmt_visit(&v, stmt);
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user