Fix more nocode_wanted jump problems

In statement expression we really mustn't emit backward jumps
under nocode_wanted (they will form infinte loops as no expressions
are evaluated).  Do-while and explicit loop with gotos weren't
handled.
master
Michael Matz 2016-09-04 05:17:08 +02:00
parent f2a071e808
commit 1602998751
3 changed files with 46 additions and 4 deletions

View File

@ -5605,8 +5605,9 @@ static void block(int *bsym, int *csym, int is_expr)
skip('(');
gsym(b);
gexpr();
c = gvtst(0, 0);
gsym_addr(c, d);
c = gvtst(0, 0);
if (!nocode_wanted)
gsym_addr(c, d);
skip(')');
gsym(a);
skip(';');
@ -5678,7 +5679,10 @@ static void block(int *bsym, int *csym, int is_expr)
gexpr();
if ((vtop->type.t & VT_BTYPE) != VT_PTR)
expect("pointer");
ggoto();
if (!nocode_wanted)
ggoto();
else
vtop--;
} else if (tok >= TOK_UIDENT) {
s = label_find(tok);
/* put forward definition if needed */
@ -5689,7 +5693,9 @@ static void block(int *bsym, int *csym, int is_expr)
s->r = LABEL_FORWARD;
}
vla_sp_restore_root();
if (s->r & LABEL_FORWARD)
if (nocode_wanted)
;
else if (s->r & LABEL_FORWARD)
s->jnext = gjmp(s->jnext);
else
gjmp_addr(s->jnext);

View File

@ -27,6 +27,36 @@ static void kb_wait_2(void)
timeout--;
} while (timeout);
}
static void kb_wait_2_1(void)
{
unsigned long timeout = 2;
do {
(1 ?
printf("timeout=%ld\n", timeout) :
({
do {
printf("error\n");
} while (1);
})
);
timeout--;
} while (timeout);
}
static void kb_wait_2_2(void)
{
unsigned long timeout = 2;
do {
(1 ?
printf("timeout=%ld\n", timeout) :
({
label:
printf("error\n");
goto label;
})
);
timeout--;
} while (timeout);
}
static void kb_wait_3(void)
{
unsigned long timeout = 2;
@ -73,6 +103,8 @@ int main()
printf("begin\n");
kb_wait_1();
kb_wait_2();
kb_wait_2_1();
kb_wait_2_2();
kb_wait_3();
kb_wait_4();
printf("end\n");

View File

@ -7,4 +7,8 @@ timeout=2
timeout=1
timeout=2
timeout=1
timeout=2
timeout=1
timeout=2
timeout=1
end