ref: e2baffe488c080950e5ffdd25989e6f249f28c5f
parent: 40478b756a78ca52baeb4650269e6cdc313dac17
author: Ori Bernstein <[email protected]>
date: Sun Aug 5 18:01:09 EDT 2012
Squash indirection bugs.
--- a/6/isel.c
+++ b/6/isel.c
@@ -495,9 +495,7 @@
case Oderef:
a = selexpr(s, args[0]);
a = inr(s, a);
- r = locreg(mode(n));
- c = locmem(0, a, Rnone, mode(n));
- g(s, Imov, c, r, NULL);
+ r = locmem(0, a, Rnone, mode(n));
break;
case Oaddr:
@@ -534,16 +532,12 @@
die("Unimplemented op %s", opstr(exprop(n)));
break;
case Oset:
- assert(exprop(args[0]) == Ovar);
+ assert(exprop(args[0]) == Ovar || exprop(args[0]) == Oderef);
b = selexpr(s, args[1]);
- a = selexpr(s, args[0]);
- b = inri(s, b);
- g(s, Imov, b, a, NULL);
- r = b;
- break;
- case Ostor: /* reg -> mem */
- b = selexpr(s, args[1]);
- a = memloc(s, args[0], mode(args[0]));
+ if (exprop(args[0]) == Oderef)
+ a = memloc(s, args[0]->expr.args[0], mode(n));
+ else
+ a = selexpr(s, args[0]);
b = inri(s, b);
g(s, Imov, b, a, NULL);
r = b;
--- a/6/simp.c
+++ b/6/simp.c
@@ -131,27 +131,27 @@
return n;
}
-static Node *set(Node *a, Node *b)
+static Node *deref(Node *a)
{
Node *n;
- assert(a != NULL && b != NULL);
- assert(exprop(a) == Ovar);
- n = mkexpr(a->line, Oset, a, b, NULL);
+ assert(a->expr.type->type == Typtr);
+ n = mkexpr(a->line, Oderef, a, NULL);
+ n->expr.type = base(a->expr.type);
return n;
}
-Node *store(Node *a, Node *b)
+static Node *set(Node *a, Node *b)
{
Node *n;
assert(a != NULL && b != NULL);
- assert(tybase(exprtype(a))->type == Typtr);
- n = mkexpr(a->line, Ostor, a, b, NULL);
+ assert(exprop(a) == Ovar || exprop(a) == Oderef);
+ n = mkexpr(a->line, Oset, a, b, NULL);
+ n->expr.type = exprtype(a);
return n;
}
-
static Node *disp(int line, uint v)
{
Node *n;
@@ -670,9 +670,9 @@
switch (exprop(n)) {
case Ovar: r = n; break;
- case Oidx: r = idxaddr(s, n); break;
- case Oderef: r = rval(s, n->expr.args[0], NULL); break;
- case Omemb: r = membaddr(s, n); break;
+ case Oidx: r = deref(idxaddr(s, n)); break;
+ case Oderef: r = deref(rval(s, n->expr.args[0], NULL)); break;
+ case Omemb: r = deref(membaddr(s, n)); break;
default:
die("%s cannot be an lval", opstr(exprop(n)));
break;
@@ -774,14 +774,14 @@
/* we can be storing through a pointer, in the case
* of '*foo = bar'. */
if (tybase(exprtype(t))->type == Typtr) {
- stbase = store(simpcast(s, t, mktyptr(t->line, tyintptr)), base);
+ stbase = set(simpcast(s, t, mktyptr(t->line, tyintptr)), base);
sz = addk(simpcast(s, t, mktyptr(t->line, tyintptr)), Ptrsz);
} else {
- stbase = store(addr(t, tyintptr), base);
+ stbase = set(deref(addr(t, tyintptr)), base);
sz = addk(addr(t, tyintptr), Ptrsz);
}
/* *(&slice + ptrsz) = len */
- stlen = store(sz, len);
+ stlen = set(deref(sz), len);
append(s, stbase);
append(s, stlen);
return t;
@@ -852,10 +852,8 @@
u = addr(u, exprtype(lhs));
v = disp(lhs->line, size(lhs));
r = mkexpr(lhs->line, Oblit, t, u, v, NULL);
- } else if (exprop(lhs) == Ovar) {
- r = mkexpr(lhs->line, Oset, t, u, NULL);
} else {
- r = mkexpr(lhs->line, Ostor, t, u, NULL);
+ r = set(t, u);
}
}
return r;
@@ -863,7 +861,7 @@
static Node *simptup(Simp *s, Node *n, Node *dst)
{
- Node *pdst, *pval, *val, *sz, *stor, **args;
+ Node *pdst, *pval, *val, *sz, *st, **args;
Node *r;
size_t i, off;
@@ -879,11 +877,11 @@
if (stacknode(args[i])) {
sz = disp(n->line, size(val));
pval = addr(val, exprtype(val));
- stor = mkexpr(n->line, Oblit, pdst, pval, sz, NULL);
+ st = mkexpr(n->line, Oblit, pdst, pval, sz, NULL);
} else {
- stor = store(pdst, val);
+ st = set(deref(pdst), val);
}
- append(s, stor);
+ append(s, st);
off += size(args[i]);
}
return dst;
@@ -918,7 +916,7 @@
u = addr(tmp, mkty(n->line, Tyuint));
tag = mkintlit(n->line, uc->id);
tag->expr.type = mkty(n->line, Tyuint);
- append(s, store(u, tag));
+ append(s, set(deref(u), tag));
/* fill the value, if needed */
@@ -931,7 +929,7 @@
sz = disp(n->line, tysize(uc->utype));
r = mkexpr(n->line, Oblit, u, elt, sz, NULL);
} else {
- r = store(u, elt);
+ r = set(deref(u), elt);
}
append(s, r);
return tmp;
@@ -1087,10 +1085,10 @@
break;
case Oaddr:
t = lval(s, args[0]);
- if (exprop(t) == Ovar) /* Ovar is the only one that doesn't return the address directly */
+ if (exprop(t) == Ovar) /* Ovar is the only one that doesn't return Oderef(Oaddr(...)) */
r = addr(t, exprtype(t));
else
- r = t;
+ r = t->expr.args[0];
break;
default:
r = visit(s, n);
--- a/parse/infer.c
+++ b/parse/infer.c
@@ -668,7 +668,7 @@
case Olbl: /* :lbl -> void* */
settype(st, n, mktyptr(n->line, mkty(-1, Tyvoid)));
case Obad: case Ocjmp:
- case Oload: case Ostor: case Oset:
+ case Oload: case Oset:
case Oslbase: case Osllen:
case Oblit: case Numops:
case Otrunc: case Oswiden: case Ozwiden:
--- a/parse/ops.def
+++ b/parse/ops.def
@@ -54,7 +54,6 @@
/* backend-only */
O(Ocjmp, 1) /* conditional jump */
O(Oload, 1) /* load from memory */
-O(Ostor, 1) /* store through to memory */
O(Oset, 1) /* store to var */
O(Osllen, 1) /* size of slice */
O(Oslbase, 1) /* base of sice */