From 58175bb2d4b842f665f8ca9ba14ba02c4a4d8cad Mon Sep 17 00:00:00 2001 From: mike lowis Date: Thu, 22 Apr 2021 22:00:35 -0400 Subject: [PATCH] add calls to module init functions --- cerise/TODO.md | 1 + cerise/cerise.h | 9 ++++ cerise/codegen.c | 48 +++++++++------------- cerise/parser.c | 96 ++++++++++++++++++++++++------------------- cerise/tests/Module.m | 14 ++++--- cerise/tests/Module.s | 20 ++++----- 6 files changed, 101 insertions(+), 87 deletions(-) create mode 100644 cerise/TODO.md diff --git a/cerise/TODO.md b/cerise/TODO.md new file mode 100644 index 0000000..a75a7b7 --- /dev/null +++ b/cerise/TODO.md @@ -0,0 +1 @@ +* Optimize variable initialization to use constants diff --git a/cerise/cerise.h b/cerise/cerise.h index b110dbc..3d36eb4 100644 --- a/cerise/cerise.h +++ b/cerise/cerise.h @@ -107,6 +107,13 @@ typedef struct Symbol { ImmValue imm; } Symbol; +typedef struct Module { + struct Module* next; + Symbol* symbols; + char* name; + char* alias; +} Module; + typedef struct { enum { ITEM_CONST, ITEM_VAR @@ -120,6 +127,7 @@ typedef struct { LexFile* done; LexFile* file; Tok tok; + Module* imports; Symbol* scope; } Parser; @@ -152,6 +160,7 @@ void codegen_setint(Item* item, Type* type, long long val); void codegen_setreal(Item* item, double val); void codegen_setstr(Item* item, char* val); +void codegen_import(char* name); void codegen_var(char* name, Type* type); void codegen_main(char* modname); void codegen_startproc(char* name, long long localsz); diff --git a/cerise/codegen.c b/cerise/codegen.c index 18f8c4f..af270d4 100644 --- a/cerise/codegen.c +++ b/cerise/codegen.c @@ -186,29 +186,23 @@ static void const_unop(int op, Item* a) } } +void codegen_import(char* name) +{ + printf(" call %s\n", name); +} + void codegen_var(char* name, Type* type) { - if (type->form == FORM_BOOL || type->form == FORM_INT) - { - printf(".data\n"); - printf("%s:\n", name); - printf(" .zero %d\n\n", type->size); - } - else if (type->form == FORM_REAL) - { - } - else - { - assert(!"not supported"); - } + printf(" .data\n"); + printf("%s:\n", name); + printf(" .zero %d\n\n", type->size); } void codegen_main(char* modname) { codegen_startproc("main", 0); -// op_l (OP_CALL, modname); - printf(" call %s\n", modname); - printf(" xor %%rax, %%rax\n"); + printf(" call %s\n", modname); + printf(" xor %%rax, %%rax\n"); codegen_endproc(); } @@ -218,27 +212,22 @@ void codegen_startproc(char* name, long long localsz) printf(" .globl %s\n", name); printf("%s:\n", name); -// op_r (OP_PUSH, RBP); - printf(" pushq %%rbp\n"); + printf(" pushq %%rbp\n"); if (localsz > 0) { -// op_rr (OP_MOVE, RSP, RBP); - printf(" movq %%rsp, %%rbp\n"); -// op_ri (OP_SUB, localsz, RSP); - printf(" sub $%lld, %%rsp\n\n", localsz); + printf(" movq %%rsp, %%rbp\n"); + printf(" sub $%lld, %%rsp\n\n", localsz); } else { -// op_rr (OP_MOVE, RSP, RBP); - printf(" movq %%rsp, %%rbp\n\n"); + printf(" movq %%rsp, %%rbp\n\n"); } } void codegen_endproc(void) { -// op_r (OP_POP, RBP); -// op_0 (OP_RET); - printf("\n pop %%rbp\n"); + puts(""); + printf(" pop %%rbp\n"); printf(" ret\n\n"); } @@ -346,7 +335,10 @@ void codegen_store(Item* a, Item* b) { printf(" movq $%lld, %s(%%rip)\n", b->imm.i, a->imm.s); } - (void)a, (void)b; + else + { + assert(!"bad store op"); + } } diff --git a/cerise/parser.c b/cerise/parser.c index 58e01af..0a0cbf6 100644 --- a/cerise/parser.c +++ b/cerise/parser.c @@ -484,7 +484,7 @@ RULE(var_decl) sym = sym->next; } - if (!accept(p, ',')) + if (!matches(p, IDENT)) { break; } @@ -512,7 +512,7 @@ RULE(const_decl) sym->imm = item->imm; sym->type = item->type; - if (!accept(p, ',')) + if (!matches(p, IDENT)) { break; } @@ -592,63 +592,56 @@ RULE(statement_seq) /* TODO: add function calls and other complex stuff */ error(p, "expected assignment"); } + expect(p, ';'); } else if (matches(p, IF)) { + assert("!not implemented"); } else { error(p, "expected a statement"); } - expect(p, ';'); - if (matches_oneof(p, (int[]){END, 0})) + + if (matches(p, END)) { break; } } } -RULE(declaration_seq) -{ - if (accept(p, CONST)) - { - const_decl(p, item); - expect(p, ';'); - } - - if (accept(p, TYPE)) - { - type_decl(p, item); - expect(p, ';'); - } - - if (accept(p, VAR)) - { - var_decl(p, item); - expect(p, ';'); - } - - /* WHILE sym = OSS.procedure DO ProcedureDecl; Check(OSS.semicolon, "; expected") END ; */ -} - RULE(import_list) { (void)item; expect(p, IMPORT); while (1) { - expect(p, IDENT); + Module* m = calloc(1, sizeof(Module)); + m->name = expect_text(p, IDENT); if (accept(p, '=')) { - expect(p, IDENT); + m->alias = m->name; + m->name = expect_text(p, IDENT); + m->next = p->imports; + p->imports = m; } - if (matches(p, ';')) + + if (!matches(p, IDENT)) { break; } - expect(p, ','); } - expect(p, ';'); + + /* reverse the list so when we init it happens in the right order */ + Module* imports = p->imports; + p->imports = NULL; + while (imports) + { + Module* m = imports; + imports = m->next; + m->next = p->imports; + p->imports = m; + } } RULE(module) @@ -656,29 +649,46 @@ RULE(module) expect(p, MODULE); char* sname = expect_text(p, IDENT); /* TODO: Check that it matches filename here */ - expect(p, ';'); + (void)sname; if (matches(p, IMPORT)) { import_list(p, item); } - declaration_seq(p, item); + if (accept(p, CONST)) + { + const_decl(p, item); + } - if (accept(p, BEGIN)) + if (accept(p, TYPE)) { - codegen_startproc("Module", 0); - statement_seq(p, item); - codegen_endproc(); + type_decl(p, item); } - expect(p, END); - char* ename = expect_text(p, IDENT); - if (strcmp(sname, ename)) + if (accept(p, VAR)) { - error(p, "Expected module name '%s', recieved '%s' instead", sname, ename); + var_decl(p, item); } - expect(p, ';'); + + codegen_startproc("Module", 0); + if (accept(p, BEGIN)) + { + for (Module* m = p->imports; m; m = m->next) + { + codegen_import(m->name); + } + statement_seq(p, item); + expect(p, END); + } + codegen_endproc(); + +// char* ename = expect_text(p, IDENT); +// if (strcmp(sname, ename)) +// { +// error(p, "Expected module name '%s', recieved '%s' instead", sname, ename); +// } +// expect(p, ';'); } static inline char* file_load(char* path) diff --git a/cerise/tests/Module.m b/cerise/tests/Module.m index 1b9e811..7699a0b 100644 --- a/cerise/tests/Module.m +++ b/cerise/tests/Module.m @@ -1,14 +1,16 @@ -module Module; +module Module + +#import +# A = Foo +# B = Bar const - A = true, + A = true B = 42 - ; var - a : Bool, + a : Bool b : Int - ; begin a = true; @@ -16,4 +18,4 @@ begin b = 24; b = B; # c = a + b; -end Module; +end diff --git a/cerise/tests/Module.s b/cerise/tests/Module.s index 72c4981..40e5fe3 100644 --- a/cerise/tests/Module.s +++ b/cerise/tests/Module.s @@ -1,34 +1,34 @@ -.data + .data a: .zero 1 -.data + .data b: .zero 8 .text .globl Module Module: - pushq %rbp - movq %rsp, %rbp + pushq %rbp + movq %rsp, %rbp movq $1, a(%rip) movq $1, a(%rip) movq $24, b(%rip) movq $42, b(%rip) - pop %rbp + pop %rbp ret .text .globl main main: - pushq %rbp - movq %rsp, %rbp + pushq %rbp + movq %rsp, %rbp - call Module - xor %rax, %rax + call Module + xor %rax, %rax - pop %rbp + pop %rbp ret -- 2.49.0