Commit ff642e29 authored by Rémy Oudompheng's avatar Rémy Oudompheng

cmd/6g, cmd/8g: eliminate extra agen for nil comparisons.

Removes an extra LEAL/LEAQ instructions there and usually saves
a useless temporary in the idiom
    if err := foo(); err != nil {...}

Generated code is also less involved:
    MOVQ err+n(SP), AX
    CMPQ AX, $0
(potentially CMPQ n(SP), $0) instead of
    LEAQ err+n(SP), AX
    CMPQ (AX), $0

Update #1914.

R=daniel.morsing, nigeltao, rsc
CC=golang-dev, remy
https://golang.org/cl/6493099
parent b19c32ac
......@@ -978,41 +978,35 @@ bgen(Node *n, int true, int likely, Prog *to)
nl = nr;
nr = r;
}
if(isslice(nl->type)) {
// only valid to cmp darray to literal nil
// front end should only leave cmp to literal nil
if((a != OEQ && a != ONE) || nr->op != OLITERAL) {
yyerror("illegal array comparison");
yyerror("illegal slice comparison");
break;
}
a = optoas(a, types[tptr]);
regalloc(&n1, types[tptr], N);
agen(nl, &n1);
n2 = n1;
n2.op = OINDREG;
n2.xoffset = Array_array;
n2.type = types[tptr];
igen(nl, &n1, N);
n1.xoffset += Array_array;
n1.type = types[tptr];
nodconst(&tmp, types[tptr], 0);
gins(optoas(OCMP, types[tptr]), &n2, &tmp);
gins(optoas(OCMP, types[tptr]), &n1, &tmp);
patch(gbranch(a, types[tptr], likely), to);
regfree(&n1);
break;
}
if(isinter(nl->type)) {
// front end shold only leave cmp to literal nil
// front end should only leave cmp to literal nil
if((a != OEQ && a != ONE) || nr->op != OLITERAL) {
yyerror("illegal interface comparison");
break;
}
a = optoas(a, types[tptr]);
regalloc(&n1, types[tptr], N);
agen(nl, &n1);
n2 = n1;
n2.op = OINDREG;
n2.xoffset = 0;
igen(nl, &n1, N);
n1.type = types[tptr];
nodconst(&tmp, types[tptr], 0);
gins(optoas(OCMP, types[tptr]), &n2, &tmp);
gins(optoas(OCMP, types[tptr]), &n1, &tmp);
patch(gbranch(a, types[tptr], likely), to);
regfree(&n1);
break;
......
......@@ -969,18 +969,15 @@ bgen(Node *n, int true, int likely, Prog *to)
if(isslice(nl->type)) {
// front end should only leave cmp to literal nil
if((a != OEQ && a != ONE) || nr->op != OLITERAL) {
yyerror("illegal array comparison");
yyerror("illegal slice comparison");
break;
}
a = optoas(a, types[tptr]);
regalloc(&n1, types[tptr], N);
agen(nl, &n1);
n2 = n1;
n2.op = OINDREG;
n2.xoffset = Array_array;
n2.type = types[tptr];
igen(nl, &n1, N);
n1.xoffset += Array_array;
n1.type = types[tptr];
nodconst(&tmp, types[tptr], 0);
gins(optoas(OCMP, types[tptr]), &n2, &tmp);
gins(optoas(OCMP, types[tptr]), &n1, &tmp);
patch(gbranch(a, types[tptr], likely), to);
regfree(&n1);
break;
......@@ -993,13 +990,10 @@ bgen(Node *n, int true, int likely, Prog *to)
break;
}
a = optoas(a, types[tptr]);
regalloc(&n1, types[tptr], N);
agen(nl, &n1);
n2 = n1;
n2.op = OINDREG;
n2.xoffset = 0;
igen(nl, &n1, N);
n1.type = types[tptr];
nodconst(&tmp, types[tptr], 0);
gins(optoas(OCMP, types[tptr]), &n2, &tmp);
gins(optoas(OCMP, types[tptr]), &n1, &tmp);
patch(gbranch(a, types[tptr], likely), to);
regfree(&n1);
break;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment