summaryrefslogtreecommitdiff
path: root/src/cmd/gc
diff options
context:
space:
mode:
authorRuss Cox <rsc@golang.org>2014-10-20 22:04:12 -0400
committerRuss Cox <rsc@golang.org>2014-10-20 22:04:12 -0400
commit2043f3b47093bc0258c14f13200a29042cf137e9 (patch)
treeb1e018f69d50ff42907b2d21f28c4c0cb2e214f7 /src/cmd/gc
parente9ab7303f127c32b2021fa360e710e8e091d62c3 (diff)
downloadgo-2043f3b47093bc0258c14f13200a29042cf137e9.tar.gz
cmd/gc: disallow call of *T method using **T variable
This brings cmd/gc in line with the spec on this question. It might break existing code, but that code was not conformant with the spec. Credit to R?my for finding the broken code. Fixes issue 6366. LGTM=r R=golang-codereviews, r CC=adonovan, golang-codereviews, gri https://codereview.appspot.com/129550043
Diffstat (limited to 'src/cmd/gc')
-rw-r--r--src/cmd/gc/typecheck.c7
1 files changed, 5 insertions, 2 deletions
diff --git a/src/cmd/gc/typecheck.c b/src/cmd/gc/typecheck.c
index 2ad8ab5bf..714c66268 100644
--- a/src/cmd/gc/typecheck.c
+++ b/src/cmd/gc/typecheck.c
@@ -2127,13 +2127,16 @@ lookdot(Node *n, Type *t, int dostrcmp)
n->left = nod(OADDR, n->left, N);
n->left->implicit = 1;
typecheck(&n->left, Etype|Erv);
- } else if(tt->etype == tptr && eqtype(tt->type, rcvr)) {
+ } else if(tt->etype == tptr && rcvr->etype != tptr && eqtype(tt->type, rcvr)) {
n->left = nod(OIND, n->left, N);
n->left->implicit = 1;
typecheck(&n->left, Etype|Erv);
- } else if(tt->etype == tptr && tt->type->etype == tptr && eqtype(derefall(tt), rcvr)) {
+ } else if(tt->etype == tptr && tt->type->etype == tptr && eqtype(derefall(tt), derefall(rcvr))) {
yyerror("calling method %N with receiver %lN requires explicit dereference", n->right, n->left);
while(tt->etype == tptr) {
+ // Stop one level early for method with pointer receiver.
+ if(rcvr->etype == tptr && tt->type->etype != tptr)
+ break;
n->left = nod(OIND, n->left, N);
n->left->implicit = 1;
typecheck(&n->left, Etype|Erv);