]> Cypherpunks repositories - gostls13.git/commitdiff
static init reenabled
authorKen Thompson <ken@golang.org>
Tue, 26 May 2009 02:40:41 +0000 (19:40 -0700)
committerKen Thompson <ken@golang.org>
Tue, 26 May 2009 02:40:41 +0000 (19:40 -0700)
R=r
OCL=29358
CL=29358

src/cmd/gc/sinit.c
src/cmd/gc/subr.c

index 836cdd452c08741333ea0438f3d9a85dd77ffee0..d8cfbbe9ff7689e24d191e78d2f29d2506dfa1e1 100644 (file)
@@ -11,6 +11,21 @@ static struct
        Type*   type;
 } xxx;
 
+enum
+{
+       TC_xxx,
+
+       TC_unknown,             // class
+       TC_struct,
+       TC_array,
+       TC_slice,
+       TC_map,
+
+       TS_start,               // state
+       TS_middle,
+       TS_end,
+};
+
 /*
  * the init code (thru initfix) reformats the
  *     var = ...
@@ -26,6 +41,23 @@ static struct
  * write the code in this form, but ...
  */
 
+static int
+typeclass(Type *t)
+{
+       if(t != T)
+       switch(t->etype) {
+       case TSTRUCT:
+               return TC_struct;
+       case TARRAY:
+               if(t->bound >= 0)
+                       return TC_array;
+               return TC_slice;
+       case TMAP:
+               return TC_map;
+       }
+       return TC_unknown;
+}
+
 void
 initlin(Node* n)
 {
@@ -78,16 +110,6 @@ sametmp(Node *n1, Node *n2)
        return 0;
 }
 
-int
-indsametmp(Node *n1, Node *n2)
-{
-       if(n1->op == OIND)
-       if(inittmp(n1->left))
-       if(n1->left->xoffset == n2->xoffset)
-               return 1;
-       return 0;
-}
-
 Node*
 findarg(Node *n, char *arg, char *fn)
 {
@@ -203,7 +225,11 @@ mapindex(Node *n)
 
        // pull all the primatives
        key = findarg(n, "key", "mapassign1");
+       if(key == N)
+               return N;
        val = findarg(n, "val", "mapassign1");
+       if(val == N)
+               return N;
        index = nodintconst(xxx.type->bound);
        xxx.type->bound++;
        dowidth(xxx.type);
@@ -227,83 +253,200 @@ mapindex(Node *n)
 // look through the whole structure
 // and substitute references of B to A.
 // some rewrite goes on also.
-int
+void
 initsub(Node *n, Node *nam)
 {
        Iter iter;
-       Node *r, *w;
-       int any;
+       Node *r, *w, *c;
+       int class, state;
+
+       // we could probably get a little more
+       // out of this if we allow minimal simple
+       // expression on the right (eg OADDR-ONAME)
+       if(n->op != ONAME)
+               return 0;
+
+       class = typeclass(nam->type);
+       state = TS_start;
+
+       switch(class) {
+       case TC_struct:
+               goto str;
+       case TC_array:
+               goto ary;
+       case TC_slice:
+               goto sli;
+       case TC_map:
+               goto map;
+       }
+       return 0;
 
-       any = 0;
-       r = listfirst(&iter, &xxx.list);
-       while(r != N) {
-               switch(r->op) {
-               case OAS:
-               case OEMPTY:
-                       if(r->left != N)
-                       switch(r->left->op) {
-                       case ONAME:
-                               if(sametmp(r->left, nam)) {
-                                       any = 1;
-                                       r->left = n;
-
-                                       w = slicerewrite(r->right);
-                                       if(w != N) {
-                                               n = w->left;    // from now on use fixed array
-                                               r->right = w;
-                                               break;
-                                       }
-
-                                       w = maprewrite(r->right);
-                                       if(w != N) {
-                                               n = w->left;    // from now on use fixed array
-                                               r->right = w;
-                                               break;
-                                       }
-                               }
-                               break;
-                       case ODOT:
-                               if(sametmp(r->left->left, nam)) {
-                                       any = 1;
-                                       r->left->left = n;
-                               }
-                               if(indsametmp(r->left->left, nam)) {
-                                       any = 1;
-                                       r->left->left->left = n;
-                               }
-                               break;
-                       case OINDEX:
-                               if(sametmp(r->left->left, nam)) {
-                                       any = 1;
-                                       r->left->left = n;
-                               }
-                               if(indsametmp(r->left->left, nam)) {
-                                       any = 1;
-                                       r->left->left->left = n;
-                               }
-                               break;
+str:
+       for(r=listfirst(&iter, &xxx.list); r != N; r = listnext(&iter)) {
+               if(r->op != OAS && r->op != OEMPTY)
+                       continue;
+
+               // optional first usage "nam = N"
+               if(r->right == N && sametmp(r->left, nam)) {
+                       if(state != TS_start) {
+                               dump("", r);
+                               fatal("initsub: str-first and state=%d", state);
+                       }
+                       state = TS_middle;
+                       r->op = OEMPTY;
+                       continue;
+               }
+
+               // last usage "n = nam"
+               if(r->left != N && sametmp(r->right, nam)) {
+                       if(state == TS_end) {
+                               dump("", r);
+                               fatal("initsub: str-last and state=%d", state);
                        }
-                       break;
-               case OCALL:
-                       // call to mapassign1
-                       // look through the parameters
-                       w = findarg(r, "hmap", "mapassign1");
+                       state = TS_end;
+                       r->op = OEMPTY;
+                       continue;
+               }
+
+               // middle usage "(nam DOT name) AS expr"
+               if(r->left->op != ODOT || !sametmp(r->left->left, nam))
+                       continue;
+               if(state == TS_end) {
+                       dump("", r);
+                       fatal("initsub: str-middle and state=%d", state);
+               }
+               state = TS_middle;
+               r->left->left = n;
+       }
+       return;
+
+ary:
+       for(r=listfirst(&iter, &xxx.list); r != N; r = listnext(&iter)) {
+               if(r->op != OAS && r->op != OEMPTY)
+                       continue;
+
+               // optional first usage "nam = N"
+               if(r->right == N && sametmp(r->left, nam)) {
+                       if(state != TS_start) {
+                               dump("", r);
+                               fatal("initsub: ary-first and state=%d", state);
+                       }
+                       state = TS_middle;
+                       r->op = OEMPTY;
+                       continue;
+               }
+
+               // last usage "n = nam"
+               if(r->left != N && sametmp(r->right, nam)) {
+                       if(state == TS_end) {
+                               dump("", r);
+                               fatal("initsub: ary-last and state=%d", state);
+                       }
+                       state = TS_end;
+                       r->op = OEMPTY;
+                       continue;
+               }
+
+               // middle usage "(nam INDEX literal) = expr"
+               if(r->left->op != OINDEX || !sametmp(r->left->left, nam))
+                       continue;
+               if(state == TS_end) {
+                       dump("", r);
+                       fatal("initsub: ary-middle and state=%d", state);
+               }
+               state = TS_middle;
+               r->left->left = n;
+       }
+       return;
+
+sli:
+       w = N;
+       for(r=listfirst(&iter, &xxx.list); r != N; r = listnext(&iter)) {
+               if(r->op != OAS && r->op != OEMPTY)
+                       continue;
+
+               // first usage "nam = (newarray CALL args)"
+               if(r->right != N && sametmp(r->left, nam)) {
+                       w = slicerewrite(r->right);
                        if(w == N)
-                               break;
-                       if(sametmp(w, nam)) {
-                               any = 1;
-                               *r = *mapindex(r);
+                               continue;
+                       if(state != TS_start) {
+                               dump("", r);
+                               fatal("initsub: ary-first and state=%d", state);
                        }
-                       if(indsametmp(w, nam)) {
-fatal("indirect map index");
-                               any = 1;
-                               w->right->left = n;
+                       state = TS_middle;
+                       r->right = w;
+                       r->left = n;
+                       continue;
+               }
+
+               // last usage "n = nam"
+               if(r->left != N && sametmp(r->right, nam)) {
+                       if(state != TS_middle) {
+                               dump("", r);
+                               fatal("initsub: ary-last and state=%d", state);
                        }
-                       break;
+                       state = TS_end;
+                       r->op = OEMPTY;
+                       continue;
+               }
+
+               // middle usage "(nam INDEX literal) = expr"
+               if(r->left->op != OINDEX || !sametmp(r->left->left, nam))
+                       continue;
+               if(state != TS_middle) {
+                       dump("", r);
+                       fatal("initsub: ary-middle and state=%d", state);
+               }
+               state = TS_middle;
+               r->left->left = w->left;
+       }
+       return;
+
+map:
+return;
+       w = N;
+       for(r=listfirst(&iter, &xxx.list); r != N; r = listnext(&iter)) {
+               if(r->op == OCALL) {
+                       // middle usage "(CALL mapassign1 key, val, map)"
+                       c = mapindex(r);
+                       if(c == N)
+                               continue;
+                       state = TS_middle;
+                       *r = *c;
+                       continue;
+               }
+               if(r->op != OAS && r->op != OEMPTY)
+                       continue;
+
+               // first usage "nam = (newmap CALL args)"
+               if(r->right != N && sametmp(r->left, nam)) {
+                       w = maprewrite(r->right);
+                       if(w == N)
+                               continue;
+                       if(state != TS_start) {
+                               dump("", r);
+                               fatal("initsub: ary-first and state=%d", state);
+                       }
+                       state = TS_middle;
+                       r->right = w;
+                       r->left = n;
+                       continue;
+               }
+
+               // last usage "n = nam"
+               if(r->left != N && sametmp(r->right, nam)) {
+                       if(state != TS_middle) {
+                               dump("", r);
+                               fatal("initsub: ary-last and state=%d", state);
+                       }
+                       state = TS_end;
+                       r->op = OEMPTY;
+                       continue;
                }
-               r = listnext(&iter);
        }
-       return any;
+       return;
+
 }
 
 Node*
@@ -312,12 +455,11 @@ initfix(Node* n)
        Iter iter;
        Node *r;
 
-//dump("prelin", n);
-
        xxx.list = N;
        initlin(n);
        xxx.list = rev(xxx.list);
-if(1)
+
+if(0)
 return xxx.list;
 
 if(debug['A'])
@@ -328,8 +470,7 @@ dump("preinitfix", xxx.list);
        while(r != N) {
                if(r->op == OAS)
                if(inittmp(r->right)) {
-                       if(initsub(r->left, r->right))
-                               r->op = OEMPTY;
+                       initsub(r->left, r->right);
                }
                r = listnext(&iter);
        }
index 38e9c6fb76fe491648686ab6fcac24b21a7be23c..d8daf13a65d1e9d27513ab64ca7fd111449a1671 100644 (file)
@@ -2382,6 +2382,7 @@ tempname(Node *n, Type *t)
        // give each tmp a different name so that there
        // a chance to registerizer them
        snprint(namebuf, sizeof(namebuf), "autotmp_%.4d", statuniqgen);
+       statuniqgen++;
        s = lookup(namebuf);
 
        memset(n, 0, sizeof(*n));