]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/5a, cmd/5c, cmd/6a, cmd/6c, cmd/8a, cmd/8c, cmd/cc: support for Native Client
authorDave Cheney <dave@cheney.net>
Wed, 26 Feb 2014 19:57:06 +0000 (06:57 +1100)
committerDave Cheney <dave@cheney.net>
Wed, 26 Feb 2014 19:57:06 +0000 (06:57 +1100)
From the original description in CL 15770043

The main change here is to consult $GOARCH.

In 6c, when GOOS=nacl, some of the more complex addressing modes must be disabled, and the BP and R15 registers must not be used.

See golang.org/s/go13nacl for design overview.

LGTM=rsc
R=golang-codereviews, gobot, rsc
CC=golang-codereviews
https://golang.org/cl/69020044

13 files changed:
src/cmd/5a/lex.c
src/cmd/5c/swt.c
src/cmd/5c/txt.c
src/cmd/6a/lex.c
src/cmd/6c/reg.c
src/cmd/6c/sgen.c
src/cmd/6c/swt.c
src/cmd/6c/txt.c
src/cmd/8a/lex.c
src/cmd/8c/swt.c
src/cmd/8c/txt.c
src/cmd/cc/cc.h
src/cmd/cc/lex.c

index 13ad1128c3bf34b82d1cce33552ebedd5b4f00bd..211f7538b5a3308260dcb6efee74c3a8e312f12e 100644 (file)
@@ -73,6 +73,12 @@ main(int argc, char *argv[])
        listinit5();
        fmtinstall('L', Lconv);
 
+       // Allow GOARCH=thestring or GOARCH=thestringsuffix,
+       // but not other values.        
+       p = getgoarch();
+       if(strncmp(p, thestring, strlen(thestring)) != 0)
+               sysfatal("cannot use %cc with GOARCH=%s", thechar, p);
+
        ensuresymb(NSYMB);
        memset(debug, 0, sizeof(debug));
        cinit();
@@ -162,7 +168,7 @@ assemble(char *file)
                errorexit();
        }
        Binit(&obuf, of, OWRITE);
-       Bprint(&obuf, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&obuf, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        Bprint(&obuf, "!\n");
 
        for(pass = 1; pass <= 2; pass++) {
index b7332a27ad34ccf532c521e44534d39086a168ce..97c2e6c84e8534087219e4c41fc0f653176c5338 100644 (file)
@@ -354,7 +354,7 @@ gextern(Sym *s, Node *a, int32 o, int32 w)
 void
 outcode(void)
 {
-       Bprint(&outbuf, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&outbuf, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        if(pragcgobuf.to > pragcgobuf.start) {
                Bprint(&outbuf, "\n");
                Bprint(&outbuf, "$$  // exports\n\n");
index 373204bf1416b074206c4a92a64c867c21f4adfc..536b810302a7b3c307180e9e9927fb31c0dd6c99 100644 (file)
 
 LinkArch       *thelinkarch = &linkarm;
 
+int thechar = '5';
+char *thestring = "arm";
+
 void
 ginit(void)
 {
        Type *t;
 
-       thechar = '5';
-       thestring = "arm";
        exregoffset = REGEXT;
        exfregoffset = FREGEXT;
        listinit();
index d81d3be50a87d9f8b2863430af183aa66ace2554..98f3e427254075f6b982c350f6faf9c99e283f91 100644 (file)
@@ -79,6 +79,12 @@ main(int argc, char *argv[])
        listinit6();
        fmtinstall('L', Lconv);
 
+       // Allow GOARCH=thestring or GOARCH=thestringsuffix,
+       // but not other values.        
+       p = getgoarch();
+       if(strncmp(p, thestring, strlen(thestring)) != 0)
+               sysfatal("cannot use %cc with GOARCH=%s", thechar, p);
+
        ensuresymb(NSYMB);
        memset(debug, 0, sizeof(debug));
        cinit();
@@ -164,7 +170,7 @@ assemble(char *file)
                errorexit();
        }
        Binit(&obuf, of, OWRITE);
-       Bprint(&obuf, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&obuf, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        Bprint(&obuf, "!\n");
 
        for(pass = 1; pass <= 2; pass++) {
index 7ca745691bd3d0d06fbcd4ff789d3a8e79032cb2..348d747b729bf3f44e28a6278d79e855e402049d 100644 (file)
@@ -717,7 +717,7 @@ addmove(Reg *r, int bn, int rn, int f)
                p1->as = AMOVB;
        if(v->etype == TSHORT || v->etype == TUSHORT)
                p1->as = AMOVW;
-       if(v->etype == TVLONG || v->etype == TUVLONG || v->etype == TIND)
+       if(v->etype == TVLONG || v->etype == TUVLONG || (v->etype == TIND && ewidth[TIND] == 8))
                p1->as = AMOVQ;
        if(v->etype == TFLOAT)
                p1->as = AMOVSS;
@@ -1373,6 +1373,8 @@ BtoR(int32 b)
 {
 
        b &= 0xffffL;
+       if(nacl)
+               b &= ~((1<<(D_BP-D_AX)) | (1<<(D_R15-D_AX)));
        if(b == 0)
                return 0;
        return bitno(b) + D_AX;
index 744a60222cd3478c0eaf92d9df35e78a888ba017..ba1c1f652d070909ade418cbb408e086ebfd0882 100644 (file)
@@ -207,7 +207,7 @@ xcom(Node *n)
                                n->addable = 8;
                        break;
                }
-               if(n->addable == 8 && !side(n)) {
+               if(n->addable == 8 && !side(n) && !nacl) {
                        indx(n);
                        l = new1(OINDEX, idx.basetree, idx.regtree);
                        l->scale = idx.scale;
index d94250aa403838f2c5c98e17d648b779e296c272..c46207d34a1861d84cf6180d3fa14d5a76240549 100644 (file)
@@ -228,7 +228,7 @@ outcode(void)
        }
        Binit(&b, f, OWRITE);
 
-       Bprint(&b, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&b, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        if(pragcgobuf.to > pragcgobuf.start) {
                Bprint(&b, "\n");
                Bprint(&b, "$$  // exports\n\n");
@@ -292,6 +292,21 @@ align(int32 i, Type *t, int op, int32 *maxalign)
                break;
 
        case Aarg1:     /* initial align of parameter */
+               if(ewidth[TIND] == 4) {
+                       if(typesu[t->etype]) {
+                               for(v = t->link; v != T; v = v->down)
+                                       o = align(o, v, Aarg1, maxalign);
+                               goto out;
+                       }
+                       w = ewidth[t->etype];
+                       if(typev[t->etype] || t->etype == TDOUBLE)
+                               w = 8;
+                       else if(w <= 0 || w >= 4)
+                               w = 4;
+                       else
+                               w = 1;
+                       break;
+               }
                w = ewidth[t->etype];
                if(w <= 0 || w >= SZ_VLONG) {
                        w = SZ_VLONG;
@@ -302,6 +317,10 @@ align(int32 i, Type *t, int op, int32 *maxalign)
 
        case Aarg2:     /* width of a parameter */
                o += t->width;
+               if(ewidth[TIND] == 4) {
+                       o = align(o, t, Aarg1, maxalign);
+                       goto out;
+               }
                w = t->width;
                if(w > SZ_VLONG)
                        w = SZ_VLONG;
@@ -315,6 +334,7 @@ align(int32 i, Type *t, int op, int32 *maxalign)
        o = xround(o, w);
        if(maxalign && *maxalign < w)
                *maxalign = w;
+out:
        if(debug['A'])
                print("align %s %d %T = %d\n", bnames[op], i, t, o);
        return o;
index e7598e18897c5b3df1a9308ac12dd8c1c5abcd84..61b333c1cbe5a126b6c15e11c3554eb868192468 100644 (file)
 
 LinkArch       *thelinkarch = &linkamd64;
 
+int thechar = '6';
+char *thestring = "amd64";
+
 void
 ginit(void)
 {
        int i;
        Type *t;
 
-       thechar = '6';
-       thestring = "amd64";
-       dodefine("_64BIT");
+       dodefine("_64BITREG");
+       if(ewidth[TIND] == 8)
+               dodefine("_64BIT");
        listinit();
        nstring = 0;
        mnstring = 0;
@@ -130,6 +133,10 @@ ginit(void)
                if(i >= D_X0 && i <= D_X7)
                        reg[i] = 0;
        }
+       if(nacl) {
+               reg[D_BP] = 1;
+               reg[D_R15] = 1;
+       }
 }
 
 void
@@ -139,6 +146,10 @@ gclean(void)
        Sym *s;
 
        reg[D_SP]--;
+       if(nacl) {
+               reg[D_BP]--;
+               reg[D_R15]--;
+       }
        for(i=D_AX; i<=D_R15; i++)
                if(reg[i])
                        diag(Z, "reg %R left allocated", i);
@@ -569,7 +580,7 @@ naddr(Node *n, Addr *a)
                }
                a->sym = nil;
                a->type = D_CONST;
-               if(typev[n->type->etype] || n->type->etype == TIND)
+               if(typev[n->type->etype] || (n->type->etype == TIND && ewidth[TIND] == 8))
                        a->offset = n->vconst;
                else
                        a->offset = convvtox(n->vconst, typeu[n->type->etype]? TULONG: TLONG);
@@ -632,6 +643,12 @@ gmove(Node *f, Node *t)
 
        ft = f->type->etype;
        tt = t->type->etype;
+       if(ewidth[TIND] == 4) {
+               if(ft == TIND)
+                       ft = TUINT;
+               if(tt == TIND)
+                       tt = TUINT;
+       }
        t64 = tt == TVLONG || tt == TUVLONG || tt == TIND;
        if(debug['M'])
                print("gop: %O %O[%s],%O[%s]\n", OAS,
@@ -723,6 +740,8 @@ gmove(Node *f, Node *t)
                goto ld;
        case TIND:
                a = AMOVQ;
+               if(ewidth[TIND] == 4)
+                       a = AMOVL;
 
        ld:
                regalloc(&nod, f, t);
@@ -1228,6 +1247,8 @@ gopcode(int o, Type *ty, Node *f, Node *t)
        et = TLONG;
        if(ty != T)
                et = ty->etype;
+       if(et == TIND && ewidth[TIND] == 4)
+               et = TUINT;
        if(debug['M']) {
                if(f != Z && f->type != T)
                        print("gop: %O %O[%s],", o, f->op, tnames[et]);
@@ -1564,7 +1585,7 @@ exreg(Type *t)
                if(exregoffset >= 64)
                        return 0;
                o = exregoffset;
-               exregoffset += 8;
+               exregoffset += ewidth[TIND];
                return o+1;     // +1 to avoid 0 == failure; naddr's case OEXREG will subtract 1.
        }
        return 0;
index b48b900b1f8e9453640d78495c2c89d422fe09f4..6c55b314357cd04b98208970771a7d93e98e57b9 100644 (file)
@@ -79,6 +79,12 @@ main(int argc, char *argv[])
        listinit8();
        fmtinstall('L', Lconv);
 
+       // Allow GOARCH=thestring or GOARCH=thestringsuffix,
+       // but not other values.        
+       p = getgoarch();
+       if(strncmp(p, thestring, strlen(thestring)) != 0)
+               sysfatal("cannot use %cc with GOARCH=%s", thechar, p);
+
        ensuresymb(NSYMB);
        memset(debug, 0, sizeof(debug));
        cinit();
@@ -163,7 +169,7 @@ assemble(char *file)
                errorexit();
        }
        Binit(&obuf, of, OWRITE);
-       Bprint(&obuf, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&obuf, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        Bprint(&obuf, "!\n");
 
        for(pass = 1; pass <= 2; pass++) {
index ae4edb810fcae5220c3e24ba879b1f64cc8286f0..54fb0881f8b54f0779a0e23b637176ef11886da2 100644 (file)
@@ -233,7 +233,7 @@ outcode(void)
        }
        Binit(&b, f, OWRITE);
 
-       Bprint(&b, "go object %s %s %s\n", getgoos(), thestring, getgoversion());
+       Bprint(&b, "go object %s %s %s\n", getgoos(), getgoarch(), getgoversion());
        if(pragcgobuf.to > pragcgobuf.start) {
                Bprint(&b, "\n");
                Bprint(&b, "$$  // exports\n\n");
index 4708785c4a7f51a614a4b49e2b03c526def60620..8a38955459785debab3c4bb5e5cba931a69d1865 100644 (file)
 
 LinkArch       *thelinkarch = &link386;
 
+int thechar = '8';
+char *thestring = "386";
+
 void
 ginit(void)
 {
        int i;
        Type *t;
 
-       thechar = '8';
-       thestring = "386";
        exregoffset = 0;
        exfregoffset = 0;
        listinit();
index ad0034a623fa0bfe4d2a0c91fd7480f16c0f006d..726364ce944829d2463758bd0afa0df0d08ae20c 100644 (file)
@@ -506,8 +506,8 @@ EXTERN      Sym*    symstring;
 EXTERN int     taggen;
 EXTERN Type*   tfield;
 EXTERN Type*   tufield;
-EXTERN int     thechar;
-EXTERN char*   thestring;
+extern int     thechar;
+extern char*   thestring;
 extern LinkArch*       thelinkarch;
 EXTERN Type*   thisfn;
 EXTERN int32   thunk;
@@ -524,6 +524,7 @@ EXTERN      int     flag_largemodel;
 EXTERN int     ncontin;
 EXTERN int     canreach;
 EXTERN int     warnreach;
+EXTERN int     nacl;
 EXTERN Bits    zbits;
 EXTERN Fmt     pragcgobuf;
 EXTERN Biobuf  bstdout;
index 163bb0f0aa718792749f17f33108014cbe8ccbf3..f6025d28073ef4fd241bb7e5f25aac8024391d11 100644 (file)
@@ -117,6 +117,19 @@ void
 main(int argc, char *argv[])
 {
        int c;
+       char *p;
+
+       // Allow GOARCH=thestring or GOARCH=thestringsuffix,
+       // but not other values.        
+       p = getgoarch();
+       if(strncmp(p, thestring, strlen(thestring)) != 0)
+               sysfatal("cannot use %cc with GOARCH=%s", thechar, p);
+       if(strcmp(getgoarch(), "amd64p32") == 0) // must be before cinit
+               ewidth[TIND] = 4;
+               
+       nacl = strcmp(getgoos(), "nacl") == 0;
+       if(nacl)
+               flag_largemodel = 1;
 
        quotefmtinstall(); // before cinit, which overrides %Q