summaryrefslogtreecommitdiff
path: root/src/cmd/8c
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/8c')
-rw-r--r--src/cmd/8c/cgen.c35
-rw-r--r--src/cmd/8c/gc.h3
-rw-r--r--src/cmd/8c/swt.c24
3 files changed, 58 insertions, 4 deletions
diff --git a/src/cmd/8c/cgen.c b/src/cmd/8c/cgen.c
index 7f02bd96e..869d31ace 100644
--- a/src/cmd/8c/cgen.c
+++ b/src/cmd/8c/cgen.c
@@ -1221,7 +1221,7 @@ void
boolgen(Node *n, int true, Node *nn)
{
int o;
- Prog *p1, *p2;
+ Prog *p1, *p2, *p3;
Node *l, *r, nod, nod1;
int32 curs;
@@ -1346,6 +1346,15 @@ boolgen(Node *n, int true, Node *nn)
cgen64(n, Z);
goto com;
}
+ if(true && typefd[l->type->etype] && (o == OEQ || o == ONE)) {
+ // Cannot rewrite !(l == r) into l != r with float64; it breaks NaNs.
+ // Jump around instead.
+ boolgen(n, 0, Z);
+ p1 = p;
+ gbranch(OGOTO);
+ patch(p1, pc);
+ goto com;
+ }
if(true)
o = comrel[relindex(o)];
if(l->complex >= FNX && r->complex >= FNX) {
@@ -1378,6 +1387,30 @@ boolgen(Node *n, int true, Node *nn)
} else
fgopcode(o, l, &fregnode0, 0, 1);
}
+ switch(o) {
+ case OEQ:
+ // Already emitted AJEQ; want AJEQ and AJPC.
+ p1 = p;
+ gbranch(OGOTO);
+ p2 = p;
+ patch(p1, pc);
+ gins(AJPC, Z, Z);
+ patch(p2, pc);
+ break;
+
+ case ONE:
+ // Already emitted AJNE; want AJNE or AJPS.
+ p1 = p;
+ gins(AJPS, Z, Z);
+ p2 = p;
+ gbranch(OGOTO);
+ p3 = p;
+ patch(p1, pc);
+ patch(p2, pc);
+ gbranch(OGOTO);
+ patch(p3, pc);
+ break;
+ }
goto com;
}
if(l->op == OCONST) {
diff --git a/src/cmd/8c/gc.h b/src/cmd/8c/gc.h
index 32b80e995..4a57f5d3c 100644
--- a/src/cmd/8c/gc.h
+++ b/src/cmd/8c/gc.h
@@ -304,7 +304,8 @@ void gpseudo(int, Sym*, Node*);
int swcmp(const void*, const void*);
void doswit(Node*);
void swit1(C1*, int, int32, Node*);
-void cas(void);
+void swit2(C1*, int, int32, Node*);
+void newcase(void);
void bitload(Node*, Node*, Node*, Node*, Node*);
void bitstore(Node*, Node*, Node*, Node*, Node*);
int32 outstring(char*, int32);
diff --git a/src/cmd/8c/swt.c b/src/cmd/8c/swt.c
index 006bfdfe2..f1ca4c25f 100644
--- a/src/cmd/8c/swt.c
+++ b/src/cmd/8c/swt.c
@@ -33,6 +33,26 @@
void
swit1(C1 *q, int nc, int32 def, Node *n)
{
+ Node nreg;
+
+ if(typev[n->type->etype]) {
+ regsalloc(&nreg, n);
+ nreg.type = types[TVLONG];
+ cgen(n, &nreg);
+ swit2(q, nc, def, &nreg);
+ return;
+ }
+
+ regalloc(&nreg, n, Z);
+ nreg.type = types[TLONG];
+ cgen(n, &nreg);
+ swit2(q, nc, def, &nreg);
+ regfree(&nreg);
+}
+
+void
+swit2(C1 *q, int nc, int32 def, Node *n)
+{
C1 *r;
int i;
Prog *sp;
@@ -58,12 +78,12 @@ swit1(C1 *q, int nc, int32 def, Node *n)
gbranch(OGOTO);
p->as = AJEQ;
patch(p, r->label);
- swit1(q, i, def, n);
+ swit2(q, i, def, n);
if(debug['W'])
print("case < %.8ux\n", r->val);
patch(sp, pc);
- swit1(r+1, nc-i-1, def, n);
+ swit2(r+1, nc-i-1, def, n);
}
void