mirror of https://github.com/golang/go.git
[dev.typeparams] go/types: better recv Var for method expressions
This is a port of CL 320489 to go/types, adjusted to be consistent about named/unnamed parameters. TestEvalPos was failing without this addition. For #46209 Change-Id: Icdf86e84ebce8ccdb7846a63b5605e360e2b8781 Reviewed-on: https://go-review.googlesource.com/c/go/+/324733 Trust: Robert Findley <rfindley@google.com> Run-TryBot: Robert Findley <rfindley@google.com> TryBot-Result: Go Bot <gobot@golang.org> Reviewed-by: Robert Griesemer <gri@golang.org>
This commit is contained in:
parent
e32fab145b
commit
62c40878e4
|
|
@ -575,17 +575,38 @@ func (check *Checker) selector(x *operand, e *ast.SelectorExpr) {
|
||||||
|
|
||||||
check.recordSelection(e, MethodExpr, x.typ, m, index, indirect)
|
check.recordSelection(e, MethodExpr, x.typ, m, index, indirect)
|
||||||
|
|
||||||
|
sig := m.typ.(*Signature)
|
||||||
|
if sig.recv == nil {
|
||||||
|
check.error(e, _InvalidDeclCycle, "illegal cycle in method declaration")
|
||||||
|
goto Error
|
||||||
|
}
|
||||||
|
|
||||||
// the receiver type becomes the type of the first function
|
// the receiver type becomes the type of the first function
|
||||||
// argument of the method expression's function type
|
// argument of the method expression's function type
|
||||||
var params []*Var
|
var params []*Var
|
||||||
sig := m.typ.(*Signature)
|
|
||||||
if sig.params != nil {
|
if sig.params != nil {
|
||||||
params = sig.params.vars
|
params = sig.params.vars
|
||||||
}
|
}
|
||||||
|
// Be consistent about named/unnamed parameters.
|
||||||
|
needName := true
|
||||||
|
for _, param := range params {
|
||||||
|
if param.Name() == "" {
|
||||||
|
needName = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
name := ""
|
||||||
|
if needName {
|
||||||
|
name = sig.recv.name
|
||||||
|
if name == "" {
|
||||||
|
name = "_"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
params = append([]*Var{NewVar(sig.recv.pos, sig.recv.pkg, name, x.typ)}, params...)
|
||||||
x.mode = value
|
x.mode = value
|
||||||
x.typ = &Signature{
|
x.typ = &Signature{
|
||||||
tparams: sig.tparams,
|
tparams: sig.tparams,
|
||||||
params: NewTuple(append([]*Var{NewVar(token.NoPos, check.pkg, "_", x.typ)}, params...)...),
|
params: NewTuple(params...),
|
||||||
results: sig.results,
|
results: sig.results,
|
||||||
variadic: sig.variadic,
|
variadic: sig.variadic,
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -187,10 +187,10 @@ func f4() (x *f4 /* ERROR "not a type" */ ) { return }
|
||||||
// TODO(#43215) this should be detected as a cycle error
|
// TODO(#43215) this should be detected as a cycle error
|
||||||
func f5([unsafe.Sizeof(f5)]int) {}
|
func f5([unsafe.Sizeof(f5)]int) {}
|
||||||
|
|
||||||
func (S0) m1 (x S0 /* ERROR value .* is not a type */ .m1) {}
|
func (S0) m1 (x S0 /* ERROR illegal cycle in method declaration */ .m1) {}
|
||||||
func (S0) m2 (x *S0 /* ERROR value .* is not a type */ .m2) {}
|
func (S0) m2 (x *S0 /* ERROR illegal cycle in method declaration */ .m2) {}
|
||||||
func (S0) m3 () (x S0 /* ERROR value .* is not a type */ .m3) { return }
|
func (S0) m3 () (x S0 /* ERROR illegal cycle in method declaration */ .m3) { return }
|
||||||
func (S0) m4 () (x *S0 /* ERROR value .* is not a type */ .m4) { return }
|
func (S0) m4 () (x *S0 /* ERROR illegal cycle in method declaration */ .m4) { return }
|
||||||
|
|
||||||
// interfaces may not have any blank methods
|
// interfaces may not have any blank methods
|
||||||
type BlankI interface {
|
type BlankI interface {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue