opt: Make break and goto not fallthrough

As we can optimize dead code a bit already it's fitting
to disable code emission after break and goto.
This commit is contained in:
Michael Matz
2016-09-26 20:31:24 +02:00
parent 31c7ea0165
commit ca435dc2e3
2 changed files with 68 additions and 2 deletions

View File

@ -5396,7 +5396,8 @@ static void block(int *bsym, int *csym, int is_expr)
nocode_wanted |= 2;
a = gvtst(1, 0);
block(bsym, csym, 0);
nocode_wanted = saved_nocode_wanted;
if (cond != 1)
nocode_wanted = saved_nocode_wanted;
c = tok;
if (c == TOK_ELSE) {
next();
@ -5406,10 +5407,12 @@ static void block(int *bsym, int *csym, int is_expr)
gsym(a);
block(bsym, csym, 0);
gsym(d); /* patch else jmp */
nocode_wanted = saved_nocode_wanted;
if (cond != 0)
nocode_wanted = saved_nocode_wanted;
} else
gsym(a);
} else if (tok == TOK_WHILE) {
int saved_nocode_wanted;
nocode_wanted &= ~2;
next();
d = ind;
@ -5420,7 +5423,9 @@ static void block(int *bsym, int *csym, int is_expr)
a = gvtst(1, 0);
b = 0;
++local_scope;
saved_nocode_wanted = nocode_wanted;
block(&a, &b, 0);
nocode_wanted = saved_nocode_wanted;
--local_scope;
if(!nocode_wanted)
gjmp_addr(d);
@ -5556,6 +5561,7 @@ static void block(int *bsym, int *csym, int is_expr)
/* jump unless last stmt in top-level block */
if (tok != '}' || local_scope != 1)
rsym = gjmp(rsym);
nocode_wanted |= 2;
} else if (tok == TOK_BREAK) {
/* compute jump */
if (!bsym)
@ -5563,6 +5569,7 @@ static void block(int *bsym, int *csym, int is_expr)
*bsym = gjmp(*bsym);
next();
skip(';');
nocode_wanted |= 2;
} else if (tok == TOK_CONTINUE) {
/* compute jump */
if (!csym)
@ -5573,6 +5580,7 @@ static void block(int *bsym, int *csym, int is_expr)
skip(';');
} else if (tok == TOK_FOR) {
int e;
int saved_nocode_wanted;
nocode_wanted &= ~2;
next();
skip('(');
@ -5607,7 +5615,9 @@ static void block(int *bsym, int *csym, int is_expr)
gsym(e);
}
skip(')');
saved_nocode_wanted = nocode_wanted;
block(&a, &b, 0);
nocode_wanted = saved_nocode_wanted;
if(!nocode_wanted)
gjmp_addr(c);
gsym(a);
@ -5617,13 +5627,16 @@ static void block(int *bsym, int *csym, int is_expr)
} else
if (tok == TOK_DO) {
int saved_nocode_wanted;
nocode_wanted &= ~2;
next();
a = 0;
b = 0;
d = ind;
vla_sp_restore();
saved_nocode_wanted = nocode_wanted;
block(&a, &b, 0);
nocode_wanted = saved_nocode_wanted;
skip(TOK_WHILE);
skip('(');
gsym(b);
@ -5637,6 +5650,7 @@ static void block(int *bsym, int *csym, int is_expr)
} else
if (tok == TOK_SWITCH) {
struct switch_t *saved, sw;
int saved_nocode_wanted = nocode_wanted;
next();
skip('(');
gexpr();
@ -5650,6 +5664,7 @@ static void block(int *bsym, int *csym, int is_expr)
saved = cur_switch;
cur_switch = &sw;
block(&a, csym, 0);
nocode_wanted = saved_nocode_wanted;
a = gjmp(a); /* add implicit break */
/* case lookup */
gsym(b);