]> Cypherpunks repositories - gostls13.git/commitdiff
cleanup getting ready for static init
authorKen Thompson <ken@golang.org>
Sun, 30 Aug 2009 21:43:33 +0000 (14:43 -0700)
committerKen Thompson <ken@golang.org>
Sun, 30 Aug 2009 21:43:33 +0000 (14:43 -0700)
R=rsc
OCL=34090
CL=34090

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

index dd641de96b4c8ee5bae50f2d0afad5d748b562d2..555f4e89021fb1d7df2b3e4b982177f15e9f9730 100644 (file)
@@ -32,19 +32,22 @@ renameinit(Node *n)
  * hand-craft the following initialization code
  *     var initdone·<file> uint8                      (1)
  *     func    Init·<file>()                          (2)
- *             if initdone·<file> {                   (3)
+ *             if initdone·<file> != 0 {              (3)
  *                     if initdone·<file> == 2                (4)
  *                             return
  *                     throw();                        (5)
  *             }
- *             initdone.<file>++;                      (6)
+ *             initdone.<file> += 1;                   (6)
  *             // over all matching imported symbols
  *                     <pkg>.init·<file>()            (7)
  *             { <init stmts> }                        (8)
  *             init·<file>()  // if any               (9)
- *             initdone.<file>++;                      (10)
+ *             initdone.<file> += 1;                   (10)
  *             return                                  (11)
  *     }
+ * note that this code cannot have an assignment
+ * statement or, because of the initflag,  it will
+ * be converted into a data statement.
  */
 int
 anyinit(NodeList *n)
@@ -119,7 +122,6 @@ fninit(NodeList *n)
        // (2)
 
        maxarg = 0;
-
        snprint(namebuf, sizeof(namebuf), "Init·");
 
        // this is a botch since we need a known name to
@@ -196,14 +198,9 @@ fninit(NodeList *n)
 
        fn->nbody = r;
 
-//dump("b", fn);
-//dump("r", fn->nbody);
-
        initflag = 1;   // flag for loader static initialization
        funcbody(fn);
        typecheck(&fn, Etop);
        funccompile(fn);
        initflag = 0;
 }
-
-
index 84e844c271c8f6b2f17993e76f951d412236d08d..da3084341e8f0f22a2f4b6020032634131259db0 100644 (file)
@@ -8,455 +8,6 @@
 
 #include       "go.h"
 
-static struct
-{
-       NodeList*       list;
-       Node*   mapname;
-       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 = ...
- * statements, rewriting the automatic
- * variables with the static variables.
- * this allows the code generator to
- * generate DATA statements instead
- * of assignment statements.
- * it is quadradic, may need to change.
- * it is extremely fragile knowing exactly
- * how the code from (struct|array|map)lit
- * will look. ideally the lit routines could
- * 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(NodeList *l)
-{
-       Node *n;
-
-       for(; l; l=l->next) {
-               n = l->n;
-               switch(n->op) {
-               case ODCLFUNC:
-               case ODCLCONST:
-               case ODCLTYPE:
-                       continue;
-               }
-               initlin(n->ninit);
-               n->ninit = nil;
-               xxx.list = list(xxx.list, n);
-               switch(n->op) {
-               default:
-                       print("o = %O\n", n->op);
-                       break;
-
-               case OCALL:
-                       // call to mapassign1
-               case OAS:
-                       break;
-               }
-       }
-}
-
-int
-inittmp(Node *n)
-{
-       if(n != N)
-       if(n->op == ONAME)
-       if(n->sym != S)
-       if(n->class == PAUTO)
-       if(memcmp(n->sym->name, "autotmp_", 8) == 0)
-               return 1;
-       return 0;
-}
-
-int
-sametmp(Node *n1, Node *n2)
-{
-       if(inittmp(n1))
-       if(n1->xoffset == n2->xoffset)
-               return 1;
-       return 0;
-}
-
-Node*
-findarg(Node *n, char *arg, char *fn)
-{
-       Node *a;
-       NodeList *l;
-
-       if(n == N || n->op != OCALL ||
-          n->left == N || n->left->sym == S ||
-          strcmp(n->left->sym->name, fn) != 0)
-               return N;
-
-       for(l=n->list; l; l=l->next) {
-               a = l->n;
-               if(a->op == OAS &&
-                  a->left != N && a->right != N &&
-                  a->left->op == OINDREG &&
-                  a->left->sym != S)
-                       if(strcmp(a->left->sym->name, arg) == 0)
-                               return a->right;
-       }
-       return N;
-}
-
-Node*
-slicerewrite(Node *n)
-{
-       Node *nel;
-       Type *t;
-       int b;
-       Node *a;
-
-       while(n->op == OCONVNOP)
-               n = n->left;
-
-       // call to makeslice - find nel argument
-       nel = findarg(n, "nel", "makeslice");
-       if(nel == N || !isslice(n->type))
-               goto no;
-
-       b = mpgetfix(nel->val.u.xval);
-       t = shallow(n->type);
-       t->bound = b;
-
-       // special hack for zero-size array
-       // invent an l-value to point at
-       if(b == 0)
-               a = staticname(types[TBOOL]);
-       else
-               a = staticname(t);
-
-       a = nod(OCOMPSLICE, a, N);
-       a->type = n->type;
-       return a;
-
-no:
-       return N;
-}
-
-Node*
-maprewrite(Node *n)
-{
-       Node *nel;
-       Type *ta, *tb;
-       Node *a;
-
-       // call to makemap - find len argument
-       nel = findarg(n, "hint", "makemap");
-       if(nel == N)
-               goto no;
-       ta = n->type;
-       if(ta->etype != TMAP)
-               goto no;
-
-       // create a new type from map[index]value
-       //      [0]struct { a index; b value) }
-
-       tb = typ(TFIELD);
-       tb->type = ta->down;
-       tb->sym = lookup("key");
-       tb->nname = newname(tb->sym);
-       tb->down = typ(TFIELD);
-       tb->down->type = ta->type;
-       tb->down->sym = lookup("val");
-       tb->down->nname = newname(tb->down->sym);
-
-       ta = typ(TSTRUCT);
-       ta->type = tb;
-
-       tb = typ(TARRAY);
-       tb->type = ta;
-       tb->bound = 0;
-
-       dowidth(tb);
-
-       a = staticname(tb);
-       a = nod(OCOMPMAP, a, N);
-       a->type = n->type;
-
-       // save stuff for this iteration
-       xxx.mapname = a->left;
-       xxx.type = tb;
-
-       return a;
-
-no:
-       return N;
-}
-
-// convert the call to mapassign1
-// into static[i].key = k, static[i].val = v
-Node*
-mapindex(Node *n)
-{
-       Node *index, *val, *key, *a, *b, *r;
-
-       // 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);
-
-       // build tree
-       a = nod(OINDEX, xxx.mapname, index);
-       a = nod(ODOT, a, newname(lookup("key")));
-       a = nod(OAS, a, key);
-
-       b = nod(OINDEX, xxx.mapname, index);
-       b = nod(ODOT, b, newname(lookup("val")));
-       b = nod(OAS, b, val);
-
-       r = liststmt(list(list1(a), b));
-       walkstmt(&r);
-       return r;
-}
-
-// for a copy out reference, A = B,
-// look through the whole structure
-// and substitute references of B to A.
-// some rewrite goes on also.
-void
-initsub(Node *n, Node *nam)
-{
-       Node *r, *w, *c;
-       NodeList *l;
-       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;
-
-       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;
-
-str:
-       for(l=xxx.list; l; l=l->next) {
-               r = l->n;
-               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);
-                       }
-                       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(l=xxx.list; l; l=l->next) {
-               r = l->n;
-               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(l=xxx.list; l; l=l->next) {
-               r = l->n;
-               if(r->op != OAS && r->op != OEMPTY)
-                       continue;
-
-               // first usage "nam = (makeslice CALL args)"
-               if(r->right != N && sametmp(r->left, nam)) {
-                       w = slicerewrite(r->right);
-                       if(w == N)
-                               continue;
-                       if(state != TS_start) {
-                               dump("", r);
-                               fatal("initsub: sli-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);
-                               setlineno(r);
-                               fatal("initsub: sli-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_middle) {
-                       dump("", r);
-                       fatal("initsub: sli-middle and state=%d", state);
-               }
-               state = TS_middle;
-               r->left->left = w->left;
-       }
-       return;
-
-map:
-return;
-       w = N;
-       for(l=xxx.list; l; l=l->next) {
-               r = l->n;
-               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 = (makemap 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: map-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: map-last and state=%d", state);
-                       }
-                       state = TS_end;
-                       r->op = OEMPTY;
-                       continue;
-               }
-       }
-       return;
-
-}
-
 static void
 init1(Node *n, NodeList **out)
 {
@@ -489,16 +40,17 @@ init1(Node *n, NodeList **out)
        n->initorder = 2;
        if(n->defn != N) {
                switch(n->defn->op) {
+               default:
+                       goto bad;
+
                case ODCLFUNC:
                        for(l=n->defn->nbody; l; l=l->next)
                                init1(l->n, out);
                        break;
+
                case OAS:
-                       if(n->defn->left != n) {
-               default:
-                               dump("defn", n->defn);
-                               fatal("bad defn");
-                       }
+                       if(n->defn->left != n)
+                               goto bad;
                        init1(n->defn->right, out);
                        if(debug['j'])
                                print("%S\n", n->sym);
@@ -508,6 +60,10 @@ init1(Node *n, NodeList **out)
        }
        n->initorder = 1;
        return;
+
+bad:
+       dump("defn", n->defn);
+       fatal("bad defn");
 }
 
 static void
@@ -532,23 +88,9 @@ initreorder(NodeList *l, NodeList **out)
 NodeList*
 initfix(NodeList *l)
 {
-       Node *r;
+       NodeList *lout;
 
-       xxx.list = nil;
-       initreorder(l, &xxx.list);
-
-if(0)
-return xxx.list;
-
-       if(nerrors != 0)
-               return xxx.list;
-
-       // look for the copy-out reference
-       for(l=xxx.list; l; l=l->next) {
-               r = l->n;
-               if(r->op == OAS)
-               if(inittmp(r->right))
-                       initsub(r->left, r->right);
-       }
-       return xxx.list;
+       lout = nil;
+       initreorder(l, &lout);
+       return lout;
 }
index 052be2a8446b4f836901ccdfa2717d7ef1d54954..9eb92f0bbdd8e5763bb27e691f8b7682d3199d46 100644 (file)
@@ -609,7 +609,7 @@ dodump(Node *n, int dep)
                print("%O-rlist\n", n->op);
                dodumplist(n->rlist, dep+1);
        }
-       if(n->nbody != nil) {
+       if(n->op != OIF && n->nbody != nil) {
                indent(dep);
                print("%O-nbody\n", n->op);
                dodumplist(n->nbody, dep+1);