]> Cypherpunks repositories - gostls13.git/commitdiff
in 6g -r (the rsc flag),
authorRuss Cox <rsc@golang.org>
Tue, 13 Jan 2009 21:46:09 +0000 (13:46 -0800)
committerRuss Cox <rsc@golang.org>
Tue, 13 Jan 2009 21:46:09 +0000 (13:46 -0800)
rewrite heap pointer moves as xchg.

R=ken
OCL=22665
CL=22665

src/cmd/6g/cgen.c
src/cmd/6g/gsubr.c
src/cmd/6g/reg.c

index 4d6e11279df919ffdaab05b643f0b20ba0f3296a..43497adb21b45b48db27637e64de554d2da952f4 100644 (file)
@@ -7,6 +7,7 @@
 /*
  * generate:
  *     res = n;
+ * simplifies and calls gmove.
  */
 void
 cgen(Node *n, Node *res)
index 553abfa605ef62f252f1eab059eaff9bbe51630a..102e27d2e156e212140f6a0c9a8274ee27451ab7 100644 (file)
@@ -511,15 +511,49 @@ gmove(Node *f, Node *t)
                goto st;
        case TINT32:
        case TUINT32:
-       case TPTR32:
                a = AMOVL;
                goto st;
        case TINT64:
        case TUINT64:
-       case TPTR64:
                a = AMOVQ;
                goto st;
 
+       case TPTR32:
+       case TPTR64:
+               /*
+                * store to pointer.
+                */
+               if(tt == TPTR32)
+                       a = AMOVL;
+               else
+                       a = AMOVQ;
+               switch(t->op) {
+               default:
+                       dump("gmove to", t);
+                       fatal("gmove t %O", t->op);
+
+               case OINDREG:
+                       if(t->val.u.reg != D_SP)
+                               goto refcount;
+                       break;
+
+               case ONAME:
+                       switch(t->class) {
+                       default:
+                               dump("gmove", t);
+                               fatal("gmove t %O class %d reg %R", t->op, t->class, t->val.u.reg);
+                       case PEXTERN:
+                       case PSTATIC:
+                               goto refcount;
+                               break;
+                       case PAUTO:
+                       case PPARAM:
+                               break;
+                       }
+                       break;
+               }
+               goto st;
+
        st:
                if(f->op == OCONST) {
                        gins(a, f, t);
@@ -532,6 +566,22 @@ gmove(Node *f, Node *t)
                regfree(&nod);
                return;
 
+       refcount:
+               if(!debug['r'])
+                       goto st;
+               // for now, mark ref count updates with AXCHGQ.
+               // using a temporary on the left, so no semantic
+               // changes.  code is likely slower, but still correct.
+               if(t64)
+                       a = AXCHGQ;
+               else
+                       a = AXCHGL;
+               regalloc(&nod, t->type, f);
+               gmove(f, &nod);
+               gins(a, &nod, t);
+               regfree(&nod);
+               return;
+
        case TFLOAT32:
                a = AMOVSS;
                goto fst;
index 2efc0dc9bf4ea5985fe044cb6deadb41365ab2f5..5b56138b3446dbb818c573c219066e8202af2895 100644 (file)
@@ -182,6 +182,19 @@ regopt(Prog *firstp)
                        for(z=0; z<BITS; z++)
                                r->use1.b[z] |= bit.b[z];
                        break;
+
+               /*
+                * left side read+write
+                */
+               case AXCHGB:
+               case AXCHGW:
+               case AXCHGL:
+               case AXCHGQ:
+                       for(z=0; z<BITS; z++) {
+                               r->use1.b[z] |= bit.b[z];
+                               r->set.b[z] |= bit.b[z];
+                       }
+                       break;
                }
 
                bit = mkvar(r, &p->to);
@@ -313,6 +326,11 @@ regopt(Prog *firstp)
                case ASBBL:
                case ASBBQ:
 
+               case AXCHGB:
+               case AXCHGW:
+               case AXCHGL:
+               case AXCHGQ:
+
                case AADDSD:
                case AADDSS:
                case ACMPSD: