From abd6d11e937b6f60191d5f79775b53a28604aa04 Mon Sep 17 00:00:00 2001 From: "Michael D. Lowis" Date: Tue, 27 Jul 2021 14:25:08 -0400 Subject: [PATCH] if statements are generating mostly-accurate graphs now. Need to prevent double visitations and ensure the blocks are printed in an appropriate order --- cerise/inc/cerise.h | 3 +- cerise/src/grammar.c | 59 +++++++++++++++++++++++++------------- cerise/src/ssa.c | 30 ++++++++++++++++++-- cerise/tests/Module.m | 66 +++++++++++++++++++++++++------------------ 4 files changed, 108 insertions(+), 50 deletions(-) diff --git a/cerise/inc/cerise.h b/cerise/inc/cerise.h index 586a61e..91d1f4f 100644 --- a/cerise/inc/cerise.h +++ b/cerise/inc/cerise.h @@ -142,6 +142,7 @@ typedef struct SsaPhi { } SsaPhi; typedef struct SsaBlock { + struct SsaBlock* next; size_t id; SsaPhi* phis; SsaNode* head; @@ -261,7 +262,7 @@ SsaNode* ssa_index(Parser* p, SsaNode* array, SsaNode* index); SsaBlock* ssa_block(Parser* p); void ssa_block_add(SsaBlock* blk, SsaNode* stmt); -SsaNode* ssa_if(SsaNode* cond, SsaBlock* br1, SsaBlock* br2); +SsaNode* ssa_if(Parser* p, SsaNode* cond, SsaBlock* br1, SsaBlock* br2); SsaNode* ssa_return(SsaNode* expr); SsaNode* ssa_call(SsaNode* func); diff --git a/cerise/src/grammar.c b/cerise/src/grammar.c index ff97f30..12076c1 100644 --- a/cerise/src/grammar.c +++ b/cerise/src/grammar.c @@ -395,26 +395,48 @@ static Type* type(Parser* p) static SsaBlock* statement_seq(Parser* p) { ENTER_RULE(); - p->curr_block = ssa_block(p); + SsaBlock* first = ssa_block(p); + first->links[0] = p->curr_join; + p->curr_block = first; do { -// if (matches(p, IF)) -// { -// expect(p, IF); -// SsaNode* cond = expression(p); -//// check_bool(p, cond); -// expect(p, THEN); -// SsaNode* blk1 = statement_seq(p); -// SsaNode* blk2 = NULL; -// if (accept(p, ELSE)) -// { -// blk2 = statement_seq(p); -// } -// ssa_block_add(block, ssa_if(cond, blk1, blk2)); -// expect(p, END); -// } -// else /* assignments/expressions */ + if (matches(p, IF)) + { + /* push a new join node */ + SsaBlock* new_join = ssa_block(p); + new_join->next = p->curr_join; + new_join->links[0] = p->curr_join; + p->curr_join = new_join; + + expect(p, IF); + SsaNode* cond = expression(p); + check_bool(p, cond); + expect(p, THEN); + SsaNode* ssa_if(p, cond); + + SsaBlock* block = p->curr_block; + block->links[0] = statement_seq(p); + /* reset vars to backup values */ + block->links[0]->links[0] = p->curr_join; + + if (accept(p, ELSE)) + { + block->links[1] = statement_seq(p); + block->links[1]->links[0] = p->curr_join; + /* reset vars to backup values */ + } + else + { + block->links[1] = p->curr_join; + } + + /* pop the join node */ + p->curr_block = p->curr_join; + p->curr_join = p->curr_join->next; + expect(p, END); + } + else /* assignments/expressions */ { SsaNode* expr = expression(p); if (accept(p, '=')) @@ -433,7 +455,7 @@ static SsaBlock* statement_seq(Parser* p) while (!matches(p, END) && !matches(p, ELSE) && !matches(p, ELSIF) && !matches(p, RETURN)); EXIT_RULE(); - return p->curr_block; + return first; } static void var_decl(Parser* p) @@ -635,7 +657,6 @@ static void module(Parser* p) { SsaBlock* seqblock = statement_seq(p); block->links[0] = seqblock; - seqblock->links[0] = p->curr_join; } expect(p, END); diff --git a/cerise/src/ssa.c b/cerise/src/ssa.c index 69ec144..1068021 100644 --- a/cerise/src/ssa.c +++ b/cerise/src/ssa.c @@ -182,7 +182,12 @@ void ssa_block_add(SsaBlock* blk, SsaNode* node) } } -SsaNode* ssa_if(SsaNode* cond, SsaBlock* br1, SsaBlock* br2); +SsaNode* ssa_if(Parser* p, SsaNode* cond, SsaBlock* br1, SsaBlock* br2) +{ + cond = load(p, cond); + return NULL; +} + SsaNode* ssa_return(SsaNode* expr); SsaNode* ssa_call(SsaNode* func); @@ -203,6 +208,19 @@ static SsaNode* binop(Parser* p, int op, SsaNode* left, SsaNode* right) node->type = left->type; node->left.var = left->dest; node->right.var = right->dest; + + /* handle comparison operators */ + switch (op) + { + case EQ: + case NEQ: + case '<': + case LTEQ: + case '>': + case GTEQ: + node->type = &BoolType; + break; + } } return node; } @@ -226,6 +244,7 @@ static SsaNode* unop(Parser* p, int op, SsaNode* operand) static SsaNode* const_binop(int op, SsaNode* a, SsaNode* b) { + printf("binop: %d %d\n", op, a->type->form); if (a->type->form == FORM_INT || a->type->form == FORM_BOOL) { switch (op) @@ -239,6 +258,7 @@ static SsaNode* const_binop(int op, SsaNode* a, SsaNode* b) case OR: a->left.val.i = a->left.val.i || b->left.val.i; break; case EQ: + puts("EQ"); a->left.val.i = a->left.val.i == b->left.val.i; a->type = &BoolType; break; @@ -535,7 +555,8 @@ static void print_block_graph(Parser* p, SsaBlock* block) ssa_print(p, node); puts(""); } - /* print the next node */ + + /* print the next nodes */ if (block->links[0]) { printf("block%lu --> block%lu\n", block->id, block->links[0]->id); @@ -544,7 +565,10 @@ static void print_block_graph(Parser* p, SsaBlock* block) if (block->links[1]) { printf("block%lu --> block%lu\n", block->id, block->links[1]->id); - print_block_graph(p, block->links[1]); +// if (!block->links[1]->phis) + { + print_block_graph(p, block->links[1]); + } } } diff --git a/cerise/tests/Module.m b/cerise/tests/Module.m index 150d972..1b08561 100644 --- a/cerise/tests/Module.m +++ b/cerise/tests/Module.m @@ -6,30 +6,30 @@ import const A* = true - B* = 42 - C* = 42.0 - D = -B - E = -C - F = not A - G = B + 2 - 2 * 2 - H = false or A +# B* = 42 +# C* = 42.0 +# D = -B +# E = -C +# F = not A +# G = B + 2 - 2 * 2 +# H = false or A -type - TypeA* = Int - TypeB* = array 5*B of Int - TypeC* = array 5 of array 10 of Int - TypeD* = record - x,y : Int - label : array 10 of Int - dim : record - w,h : Int - end - end - TypeE* = record - i : Int - a : array 5 of Int - end - TypeF* = array 5 of TypeE +#type +# TypeA* = Int +# TypeB* = array 5*B of Int +# TypeC* = array 5 of array 10 of Int +# TypeD* = record +# x,y : Int +# label : array 10 of Int +# dim : record +# w,h : Int +# end +# end +# TypeE* = record +# i : Int +# a : array 5 of Int +# end +# TypeF* = array 5 of TypeE var a* : Bool @@ -37,9 +37,9 @@ var c : Int d : Real e : array 5 of array 10 of Int - f : TypeD +# f : TypeD g : array 5 of Int - h : TypeF +# h : TypeF #procedure Foo*(e : Int, z : Int, q1 : TypeD, q2 : array 5 of Int) : Int # const FOO = 2 @@ -70,8 +70,20 @@ var begin b = 42; - b = -b; - c = b + 1; +# b = -b; +# c = b + 1; + + if c == b then + c = 42; + else + c = 24; + end + + if c == b then + b = 42; + else + b = 24; + end # h[1].i = 42; -- 2.49.0