mirror of
https://github.com/golang/go
synced 2024-11-25 21:47:59 -07:00
bug with interaction of variables
declared in cases and heap allocation R=r OCL=26064 CL=26064
This commit is contained in:
parent
b2e91a9a29
commit
0c4f4587d7
@ -787,7 +787,9 @@ mkvar(Reg *r, Adr *a)
|
||||
s = a->sym;
|
||||
if(s == S)
|
||||
goto none;
|
||||
if(s->name[0] == '!' || s->name[0] == '.')
|
||||
// if(s->name[0] == '!')
|
||||
// goto none;
|
||||
if(s->name[0] == '.')
|
||||
goto none;
|
||||
et = a->etype;
|
||||
o = a->offset;
|
||||
|
@ -189,7 +189,6 @@ casebody(Node *sw)
|
||||
br = nod(OBREAK, N, N);
|
||||
|
||||
loop:
|
||||
|
||||
if(t == N) {
|
||||
if(oc == N && os != N)
|
||||
yyerror("first switch statement must be a case");
|
||||
@ -259,12 +258,12 @@ loop:
|
||||
* rebulid case statements into if .. goto
|
||||
*/
|
||||
void
|
||||
prepsw(Node *sw, int arg)
|
||||
exprswitch(Node *sw, int arg)
|
||||
{
|
||||
Iter save;
|
||||
Node *name, *bool, *cas;
|
||||
Node *t, *a;
|
||||
//dump("prepsw before", sw->nbody->left);
|
||||
//dump("exprswitch before", sw->nbody->left);
|
||||
|
||||
cas = N;
|
||||
name = N;
|
||||
@ -281,7 +280,7 @@ prepsw(Node *sw, int arg)
|
||||
loop:
|
||||
if(t == N) {
|
||||
sw->nbody->left = rev(cas);
|
||||
//dump("prepsw after", sw->nbody->left);
|
||||
//dump("exprswitch after", sw->nbody->left);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -291,6 +290,16 @@ loop:
|
||||
goto loop;
|
||||
}
|
||||
|
||||
// pull out the dcl in case this
|
||||
// variable is allocated on the heap.
|
||||
// this should be done better to prevent
|
||||
// multiple (unused) heap allocations per switch.
|
||||
if(t->ninit != N && t->ninit->op == ODCL) {
|
||||
//dump("exprswitch case init", t->ninit);
|
||||
cas = list(cas, t->ninit);
|
||||
t->ninit = N;
|
||||
}
|
||||
|
||||
if(t->left->op == OAS) {
|
||||
if(bool == N) {
|
||||
bool = nod(OXXX, N, N);
|
||||
@ -394,6 +403,18 @@ loop:
|
||||
goto loop;
|
||||
}
|
||||
|
||||
// pull out the dcl in case this
|
||||
// variable is allocated on the heap.
|
||||
// this should be done better to prevent
|
||||
// multiple (unused) heap allocations per switch.
|
||||
// not worth doing now -- make a binary search
|
||||
// on contents of signature instead.
|
||||
if(t->ninit != N && t->ninit->op == ODCL) {
|
||||
//dump("typeswitch case init", t->ninit);
|
||||
cas = list(cas, t->ninit);
|
||||
t->ninit = N;
|
||||
}
|
||||
|
||||
a = t->left->left; // var
|
||||
a = nod(OLIST, a, bool); // var,bool
|
||||
|
||||
@ -476,7 +497,7 @@ walkswitch(Node *sw)
|
||||
/*
|
||||
* convert the switch into OIF statements
|
||||
*/
|
||||
prepsw(sw, arg);
|
||||
exprswitch(sw, arg);
|
||||
walkstate(sw->nbody);
|
||||
//print("normal done\n");
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user