summaryrefslogtreecommitdiff
path: root/src/cmd/gc/pgen.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/gc/pgen.c')
-rw-r--r--src/cmd/gc/pgen.c50
1 files changed, 42 insertions, 8 deletions
diff --git a/src/cmd/gc/pgen.c b/src/cmd/gc/pgen.c
index f2b75d61b..df8903baf 100644
--- a/src/cmd/gc/pgen.c
+++ b/src/cmd/gc/pgen.c
@@ -14,11 +14,12 @@ compile(Node *fn)
{
Plist *pl;
Node nod1, *n;
- Prog *ptxt;
+ Prog *plocals, *ptxt, *p, *p1;
int32 lno;
Type *t;
Iter save;
vlong oldstksize;
+ NodeList *l;
if(newproc == N) {
newproc = sysfunc("newproc");
@@ -29,16 +30,19 @@ compile(Node *fn)
throwreturn = sysfunc("throwreturn");
}
- if(fn->nbody == nil)
- return;
+ lno = setlineno(fn);
+
+ if(fn->nbody == nil) {
+ if(pure_go || memcmp(fn->nname->sym->name, "init·", 6) == 0)
+ yyerror("missing function body", fn);
+ goto ret;
+ }
saveerrors();
// set up domain for labels
clearlabels();
- lno = setlineno(fn);
-
curfn = fn;
dowidth(curfn->type);
@@ -63,6 +67,10 @@ compile(Node *fn)
walk(curfn);
if(nerrors != 0)
goto ret;
+ if(flag_race)
+ racewalk(curfn);
+ if(nerrors != 0)
+ goto ret;
continpc = P;
breakpc = P;
@@ -76,15 +84,34 @@ compile(Node *fn)
ptxt = gins(ATEXT, isblank(curfn->nname) ? N : curfn->nname, &nod1);
if(fn->dupok)
ptxt->TEXTFLAG = DUPOK;
- afunclit(&ptxt->from);
+ afunclit(&ptxt->from, curfn->nname);
ginit();
+
+ plocals = gins(ALOCALS, N, N);
+
+ for(t=curfn->paramfld; t; t=t->down)
+ gtrack(tracksym(t->type));
+
+ for(l=fn->dcl; l; l=l->next) {
+ n = l->n;
+ if(n->op != ONAME) // might be OTYPE or OLITERAL
+ continue;
+ switch(n->class) {
+ case PAUTO:
+ case PPARAM:
+ case PPARAMOUT:
+ nodconst(&nod1, types[TUINTPTR], l->n->type->width);
+ p = gins(ATYPE, l->n, &nod1);
+ p->from.gotype = ngotype(l->n);
+ break;
+ }
+ }
+
genlist(curfn->enter);
retpc = nil;
if(hasdefer || curfn->exit) {
- Prog *p1;
-
p1 = gjmp(nil);
retpc = gjmp(nil);
patch(p1, pc);
@@ -111,6 +138,7 @@ compile(Node *fn)
gclean();
if(nerrors != 0)
goto ret;
+
pc->as = ARET; // overwrite AEND
pc->lineno = lineno;
@@ -120,6 +148,10 @@ compile(Node *fn)
oldstksize = stksize;
allocauto(ptxt);
+
+ plocals->to.type = D_CONST;
+ plocals->to.offset = stksize;
+
if(0)
print("allocauto: %lld to %lld\n", oldstksize, (vlong)stksize);
@@ -177,8 +209,10 @@ allocauto(Prog* ptxt)
ll = curfn->dcl;
n = ll->n;
if (n->class == PAUTO && n->op == ONAME && !n->used) {
+ // No locals used at all
curfn->dcl = nil;
stksize = 0;
+ fixautoused(ptxt);
return;
}