ref: 5cc0256ea7e075ec951904e3cfcfcd30e0df31d4
parent: eb12bd70592fe92197ceec3bbfd8d064ad273a33
author: Roberto E. Vargas Caballero <[email protected]>
date: Wed Jul 9 08:25:34 EDT 2014
Simplify stmt We can use a function pointer for this function, but then we need to pass the state to all the possible statements. This is not a problem, because we can ignore the parameters we are not using, and the code of stmt will be smaller because we have only one function call.
--- a/cc1/stmt.c
+++ b/cc1/stmt.c
@@ -43,7 +43,7 @@
}
static void
-stmtexp(void)
+stmtexp(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
if (yytoken != ';')
emitexp(expr());
@@ -62,7 +62,7 @@
}
static void
-While(Caselist *lswitch)
+While(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
Symbol *begin, *cond, *end;
Node *np;
@@ -84,7 +84,7 @@
}
static void
-For(Caselist *lswitch)
+For(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
Symbol *begin, *cond, *end;
Node *econd = NULL, *einc = NULL;
@@ -117,7 +117,7 @@
}
static void
-Dowhile(Caselist *lswitch)
+Dowhile(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
Symbol *begin = label("", 1), *end = label("", 1);
@@ -132,7 +132,7 @@
}
static void
-Return(void)
+Return(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
Node *np;
Type *tp = curfun->type->type;
@@ -155,7 +155,7 @@
}
static void
-Break(Symbol *lbreak)
+Break(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
expect(BREAK);
if (!lbreak)
@@ -164,17 +164,20 @@
expect(';');
}
+static void stmt(Symbol *lbreak, Symbol *lcont, Caselist *lswitch);
+
static void
-Label(void)
+Label(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
emitlabel(label(yytext, 1));
expect(IDEN);
expect(':');
+ stmt(lbreak, lcont, lswitch);
}
static void
-Continue(Symbol *lcont)
+Continue(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
expect(CONTINUE);
if (!lcont)
@@ -184,7 +187,7 @@
}
static void
-Goto(void)
+Goto(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
expect(GOTO);
@@ -196,13 +199,14 @@
}
static void
-Switch(Symbol *lcont)
+Switch(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
Caselist lcase = {.nr = 0, .head = NULL, .deflabel = NULL};
struct scase *p;
- Symbol *lbreak = label("", 1), *lcond = label("", 1);
Node *cond;
+ Symbol *lcond = label("", 1);
+ lbreak = label("", 1);
expect(SWITCH);
expect ('(');
cond = eval(expr());
@@ -298,27 +302,24 @@
static void
stmt(Symbol *lbreak, Symbol *lcont, Caselist *lswitch)
{
+ void (*fun)(Symbol *lbreak, Symbol *lcont, Caselist *lswitch);
-repeat:
switch (yytoken) {
- case '{': context(lbreak, lcont, lswitch); break;
- case RETURN: Return(); break;
- case WHILE: While(lswitch); break;
- case FOR: For(lswitch); break;
- case DO: Dowhile(lswitch); break;
- case IF: If(lbreak, lcont, lswitch); break;
- case BREAK: Break(lbreak); break;
- case CONTINUE: Continue(lcont); break;
- case GOTO: Goto(); break;
- case SWITCH: Switch(lcont); break;
- case CASE: Case(lbreak, lcont, lswitch); break;
- case DEFAULT: Default(lbreak, lcont, lswitch); break;
- case IDEN:
- if (ahead() == ':') {
- Label();
- goto repeat;
- }
- default: stmtexp(); break;
+ case '{': fun = context; break;
+ case RETURN: fun = Return; break;
+ case WHILE: fun = While; break;
+ case FOR: fun = For; break;
+ case DO: fun = Dowhile; break;
+ case IF: fun = If; break;
+ case BREAK: fun = Break; break;
+ case CONTINUE: fun = Continue; break;
+ case GOTO: fun = Goto; break;
+ case SWITCH: fun = Switch; break;
+ case CASE: fun = Case; break;
+ case DEFAULT: fun = Default; break;
+ default: fun = stmtexp; break;
+ case IDEN: fun = (ahead() == ':') ? Label : stmtexp; break;
}
+ (*fun)(lbreak, lcont, lswitch);
}