vc: handle 64 bit mixedmode asop

This commit is contained in:
cinap_lenrek 2015-10-04 20:08:10 +02:00
parent 8e41723741
commit b556e87e08
2 changed files with 46 additions and 27 deletions

View file

@ -1,5 +1,7 @@
#include "gc.h" #include "gc.h"
static void genasop(int, Node*, Node*, Node*);
void void
cgen(Node *n, Node *nn) cgen(Node *n, Node *nn)
{ {
@ -208,7 +210,7 @@ cgen(Node *n, Node *nn)
nod2 = *l; nod2 = *l;
regalloc(&nod, r, nn); regalloc(&nod, r, nn);
gopcode(OAS, &nod2, Z, &nod); gopcode(OAS, &nod2, Z, &nod);
gopcode(o, r, Z, &nod); gopcode(o, l, Z, &nod);
gopcode(OAS, &nod, Z, &nod2); gopcode(OAS, &nod, Z, &nod2);
regfree(&nod); regfree(&nod);
@ -216,6 +218,8 @@ cgen(Node *n, Node *nn)
regfree(&nod2); regfree(&nod2);
break; break;
} }
genasop(o, l, r, nn);
break;
case OASLMUL: case OASLMUL:
case OASLDIV: case OASLDIV:
@ -225,32 +229,7 @@ cgen(Node *n, Node *nn)
case OASMOD: case OASMOD:
if(l->op == OBIT) if(l->op == OBIT)
goto asbitop; goto asbitop;
if(l->complex >= r->complex) { genasop(o, l, r, nn);
if(l->addable < INDEXED)
reglcgen(&nod2, l, Z);
else
nod2 = *l;
regalloc(&nod1, r, Z);
cgen(r, &nod1);
} else {
regalloc(&nod1, r, Z);
cgen(r, &nod1);
if(l->addable < INDEXED)
reglcgen(&nod2, l, Z);
else
nod2 = *l;
}
regalloc(&nod, n, nn);
gmove(&nod2, &nod);
gopcode(o, &nod1, Z, &nod);
gmove(&nod, &nod2);
if(nn != Z)
gopcode(OAS, &nod, Z, nn);
regfree(&nod);
regfree(&nod1);
if(l->addable < INDEXED)
regfree(&nod2);
break; break;
asbitop: asbitop:
@ -521,6 +500,43 @@ cgen(Node *n, Node *nn)
cursafe = curs; cursafe = curs;
} }
static void
genasop(int o, Node *l, Node *r, Node *nn)
{
Node nod, nod1, nod2;
int hardleft;
hardleft = l->addable < INDEXED || l->complex >= FNX;
if(l->complex >= r->complex) {
if(hardleft)
reglcgen(&nod2, l, Z);
else
nod2 = *l;
regalloc(&nod1, r, Z);
cgen(r, &nod1);
} else {
regalloc(&nod1, r, Z);
cgen(r, &nod1);
if(hardleft)
reglcgen(&nod2, l, Z);
else
nod2 = *l;
}
if(nod1.type == nod2.type || !typefd[nod1.type->etype])
regalloc(&nod, &nod2, nn);
else
regalloc(&nod, &nod1, Z);
gmove(&nod2, &nod);
gopcode(o, &nod1, Z, &nod);
gmove(&nod, &nod2);
if(nn != Z)
gmove(&nod, nn);
regfree(&nod);
regfree(&nod1);
if(hardleft)
regfree(&nod2);
}
void void
reglcgen(Node *t, Node *n, Node *nn) reglcgen(Node *t, Node *n, Node *nn)
{ {

View file

@ -557,6 +557,9 @@ gmove(Node *f, Node *t)
ft = f->type->etype; ft = f->type->etype;
tt = t->type->etype; tt = t->type->etype;
if(debug['M'])
print("gop: %O %O[%s],%O[%s]\n", OAS,
f->op, tnames[ft], t->op, tnames[tt]);
if(ft == TDOUBLE && f->op == OCONST) { if(ft == TDOUBLE && f->op == OCONST) {
d = f->fconst; d = f->fconst;