X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=codeb%2Fparser.y;h=7d9af97417b0c5a81b5baa2296f4e3a7de7620b4;hb=c21f667bead452ca940e6aa741c149ee7fb170a0;hp=cda1e7bfcf500e6b653db7512b7b98c621338dd3;hpb=128163389fedc8bc6029a0efd522ba286eff0c9a;p=uebersetzerbau-ss10.git diff --git a/codeb/parser.y b/codeb/parser.y index cda1e7b..7d9af97 100644 --- a/codeb/parser.y +++ b/codeb/parser.y @@ -23,6 +23,10 @@ * geht nicht, weil verschachtelte macros deaktiviert sind */ @end +@macro lblcountinout() + @i @Statement.lblcnt_out@ = @Statement.lblcnt_in@; +@end + /* beschreibung der attribute * s: symboltabelle * f: symboltabelle fuer quirks mit structur und parameter @@ -41,11 +45,11 @@ @attributes { struct symbol *f; } Program Structdef; @attributes { struct symbol *f; int offsetcount; } FeldID @attributes { struct symbol *s; } Methoddef -@attributes { struct symbol *s; int gparamges; } Statseq Exprs +@attributes { struct symbol *s; int gparamges; } Exprs +@attributes { struct symbol *s; int gparamges; int lblcnt_in; int lblcnt_out; } Statseq Elsestat @attributes { struct symbol *s; int gparamges; struct treenode *node; short imm; } Expr Minusterm Multerm Orterm Feld Term @attributes { struct symbol *s; int gparamges; struct treenode *node; } Lexpr -@attributes { struct symbol *sin; int gparamges; struct symbol *sout; struct -treenode *node; int vars; } Statement +@attributes { struct symbol *sin; int gparamges; struct symbol *sout; struct treenode *node; int vars; int lblcnt_in; int lblcnt_out; } Statement @traversal @postorder c @traversal @preorder reg @@ -80,6 +84,7 @@ Methoddef: @i @Parms.parms@ = 1; @i @Statseq.s@ = tab_merge(@Methoddef.s@, @Parms.f@, 0); @i @Statseq.gparamges@ = @Parms.paramges@; + @i @Statseq.lblcnt_in@ = 0; @gen func_header(@IDENT.name@); @} ; @@ -125,17 +130,26 @@ Statseq: Statement ';' Statseq @{ @i @Statement.sin@ = @Statseq.0.s@; + @i @Statement.lblcnt_in@ = @Statseq.0.lblcnt_in@; + @i @Statseq.1.s@ = @Statement.sout@; + @i @Statseq.1.lblcnt_in@ = @Statement.lblcnt_out@; @i @Statseq.1.gparamges@ = @Statseq.0.gparamges@ + @Statement.vars@; + + @i @Statseq.0.lblcnt_out@ = @Statseq.1.lblcnt_out@; @} | + @{ + @i @Statseq.0.lblcnt_out@ = @Statseq.0.lblcnt_in@; + @} ; Statement: Lexpr ASSIGN Expr @{ statinout() + lblcountinout() xxputsin(@Lexpr.s@,) xxputsin(@Expr.s@,) @i @Statement.node@ = new_node(O_ASSIGN, @Lexpr.node@, @Expr.node@); @@ -150,6 +164,7 @@ Statement: /* tab_clone ist hier noetig, vgl. folgendes statement * > var x := x - 1; */ @i @Statement.sout@ = tab_add_symbol(tab_clone(@Statement.sin@), @IDENT.name@, S_VAR, 1, @Statement.gparamges@, -1); + lblcountinout() xxputsin(@Expr.s@,) @i @Statement.node@ = new_node(O_ASSIGN, new_param(O_ID, @IDENT.name@, TREENULL, TREENULL, @Statement.gparamges@), @Expr.node@); @@ -162,6 +177,7 @@ Statement: | Expr @{ statinout() + lblcountinout() xxputsin(@Expr.s@,) @i @Statement.node@ = TREENULL; @i @Statement.vars@ = 0; @@ -170,6 +186,8 @@ Statement: | IF Expr THEN Statseq END @{ statinout() + @i @Statseq.lblcnt_in@ = @Statement.lblcnt_in@ + 1; + @i @Statement.lblcnt_out@ = @Statseq.lblcnt_out@; xxputsin(@Expr.s@,) xxputsin(@Statseq.s@,) @@ -180,24 +198,41 @@ Statement: @gen { write_tree(@Statement.node@, 0); burm_label(@Statement.node@); burm_reduce(@Statement.node@, 1); /* TODO: kann ich mir das test wirklich wegan and davor sparen? */ - printf("\ttest %s1, %%rax\n\tjz if_end\n", "$"); + printf("\ttest %s1, %%rax\n\tjz %s_ifend_%d\n", "$", get_func_name(), @Statement.lblcnt_in@); } - @gen @revorder(1) printf("if_end:\n"); + @gen @revorder(1) printf("%s_ifend_%d:\n", get_func_name(), @Statement.lblcnt_in@); @} - | IF Expr THEN Statseq ELSE Statseq END + | IF Expr THEN Statseq Elsestat END @{ statinout() + @i @Statseq.0.lblcnt_in@ = @Statement.lblcnt_in@ + 1; + @i @Elsestat.lblcnt_in@ = @Statement.lblcnt_in@; + /* TODO: welchen wert lblcnt_out zuweisen? :/ */ + @i @Statement.lblcnt_out@ = @Statseq.lblcnt_out@; + xxputsin(@Expr.s@,) xxputsin(@Statseq.0.s@,) - xxputsin(@Statseq.1.s@,) - @i @Statement.node@ = TREENULL; + xxputsin(@Elsestat.s@,) + + @i @Statement.node@ = new_node(O_IF, @Expr.node@, TREENULL); @i @Statement.vars@ = 0; + + @reg @Statement.node@->reg = @Expr.node@->reg = next_reg((char *)NULL, @Expr.gparamges@); + @gen { + write_tree(@Statement.node@, 0); burm_label(@Statement.node@); burm_reduce(@Statement.node@, 1); + /* TODO: kann ich mir das test wirklich wegan and davor sparen? */ + printf("\ttest %s1, %%rax\n\tjz %s_ifelse_%d\n", "$", get_func_name(), @Statement.lblcnt_in@); + } + @gen @revorder(1) printf("%s_ifend_%d:\n", get_func_name(), @Statement.lblcnt_in@); @} | WHILE Expr DO Statseq END @{ statinout() + lblcountinout() + /* TODO */ + @i @Statseq.0.lblcnt_in@ = @Statement.lblcnt_in@ + 1; xxputsin(@Expr.s@,) xxputsin(@Statseq.s@,) @i @Statement.node@ = TREENULL; @@ -207,6 +242,7 @@ Statement: | RETURN Expr @{ statinout() + lblcountinout() xxputsin(@Expr.s@,) @i @Statement.vars@ = 0; @@ -217,6 +253,15 @@ Statement: @} ; +Elsestat: + ELSE Statseq + @{ + @i @Statseq.lblcnt_in@ = @Elsestat.lblcnt_in@ + 1; + @i @Elsestat.lblcnt_out@ = @Statseq.lblcnt_out@; + + @gen printf("\tjmp %s_ifend_%d\n%s_ifelse_%d:\n", get_func_name(), @Elsestat.lblcnt_in@, get_func_name(), @Elsestat.lblcnt_in@); + @} + Lexpr: IDENT @{