mirror of
https://github.com/golang/go.git
synced 2025-12-08 06:10:04 +00:00
cmd/compile: make sure that the names created for instantiated type are the same
Now we have two functions that create names for instantiated types. They are inconsistent when dealing with byte/rune type. This CL makes instTypeName2 reuse the code of typecheck.InstTypeName Fixes #48198 Change-Id: I4c216b532cba6618ef9b63fd0b76e8f1c0ed7a75 Reviewed-on: https://go-review.googlesource.com/c/go/+/347491 Reviewed-by: Dan Scales <danscales@google.com> Trust: Dan Scales <danscales@google.com> Trust: Keith Randall <khr@golang.org> Run-TryBot: Dan Scales <danscales@google.com> TryBot-Result: Go Bot <gobot@golang.org>
This commit is contained in:
parent
a1938435d6
commit
6226020c2f
2 changed files with 29 additions and 25 deletions
|
|
@ -5,7 +5,6 @@
|
||||||
package noder
|
package noder
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
|
||||||
"cmd/compile/internal/base"
|
"cmd/compile/internal/base"
|
||||||
"cmd/compile/internal/ir"
|
"cmd/compile/internal/ir"
|
||||||
"cmd/compile/internal/typecheck"
|
"cmd/compile/internal/typecheck"
|
||||||
|
|
@ -72,29 +71,12 @@ func (g *irgen) typ1(typ types2.Type) *types.Type {
|
||||||
|
|
||||||
// instTypeName2 creates a name for an instantiated type, base on the type args
|
// instTypeName2 creates a name for an instantiated type, base on the type args
|
||||||
// (given as types2 types).
|
// (given as types2 types).
|
||||||
func instTypeName2(name string, targs *types2.TypeList) string {
|
func (g *irgen) instTypeName2(name string, targs *types2.TypeList) string {
|
||||||
b := bytes.NewBufferString(name)
|
rparams := make([]*types.Type, targs.Len())
|
||||||
b.WriteByte('[')
|
for i := range rparams {
|
||||||
n := targs.Len()
|
rparams[i] = g.typ(targs.At(i))
|
||||||
for i := 0; i < n; i++ {
|
|
||||||
targ := targs.At(i)
|
|
||||||
if i > 0 {
|
|
||||||
b.WriteByte(',')
|
|
||||||
}
|
}
|
||||||
// Include package names for all types, including typeparams, to
|
return typecheck.InstTypeName(name, rparams)
|
||||||
// make sure type arguments are uniquely specified.
|
|
||||||
tname := types2.TypeString(targ,
|
|
||||||
func(pkg *types2.Package) string { return pkg.Name() })
|
|
||||||
if strings.Index(tname, ", ") >= 0 {
|
|
||||||
// types2.TypeString puts spaces after a comma in a type
|
|
||||||
// list, but we don't want spaces in our actual type names
|
|
||||||
// and method/function names derived from them.
|
|
||||||
tname = strings.Replace(tname, ", ", ",", -1)
|
|
||||||
}
|
|
||||||
b.WriteString(tname)
|
|
||||||
}
|
|
||||||
b.WriteByte(']')
|
|
||||||
return b.String()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// typ0 converts a types2.Type to a types.Type, but doesn't do the caching check
|
// typ0 converts a types2.Type to a types.Type, but doesn't do the caching check
|
||||||
|
|
@ -119,7 +101,7 @@ func (g *irgen) typ0(typ types2.Type) *types.Type {
|
||||||
//
|
//
|
||||||
// When converted to types.Type, typ has a unique name,
|
// When converted to types.Type, typ has a unique name,
|
||||||
// based on the names of the type arguments.
|
// based on the names of the type arguments.
|
||||||
instName := instTypeName2(typ.Obj().Name(), typ.TArgs())
|
instName := g.instTypeName2(typ.Obj().Name(), typ.TArgs())
|
||||||
s := g.pkg(typ.Obj().Pkg()).Lookup(instName)
|
s := g.pkg(typ.Obj().Pkg()).Lookup(instName)
|
||||||
if s.Def != nil {
|
if s.Def != nil {
|
||||||
// We have already encountered this instantiation.
|
// We have already encountered this instantiation.
|
||||||
|
|
@ -314,7 +296,7 @@ func (g *irgen) fillinMethods(typ *types2.Named, ntyp *types.Type) {
|
||||||
// generic type, so we have to do a substitution to get
|
// generic type, so we have to do a substitution to get
|
||||||
// the name/type of the method of the instantiated type,
|
// the name/type of the method of the instantiated type,
|
||||||
// using m.Type().RParams() and typ.TArgs()
|
// using m.Type().RParams() and typ.TArgs()
|
||||||
inst2 := instTypeName2("", typ.TArgs())
|
inst2 := g.instTypeName2("", typ.TArgs())
|
||||||
name := meth.Sym().Name
|
name := meth.Sym().Name
|
||||||
i1 := strings.Index(name, "[")
|
i1 := strings.Index(name, "[")
|
||||||
i2 := strings.Index(name[i1:], "]")
|
i2 := strings.Index(name[i1:], "]")
|
||||||
|
|
|
||||||
22
test/typeparam/issue48198.go
Normal file
22
test/typeparam/issue48198.go
Normal file
|
|
@ -0,0 +1,22 @@
|
||||||
|
// compile -G=3
|
||||||
|
|
||||||
|
// Copyright 2021 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
package p
|
||||||
|
|
||||||
|
type Foo[T any] struct {
|
||||||
|
}
|
||||||
|
|
||||||
|
func (foo Foo[T]) Get() {
|
||||||
|
}
|
||||||
|
|
||||||
|
var(
|
||||||
|
_ = Foo[byte]{}
|
||||||
|
_ = Foo[[]byte]{}
|
||||||
|
_ = Foo[map[byte]rune]{}
|
||||||
|
|
||||||
|
_ = Foo[rune]{}
|
||||||
|
_ = Foo[[]rune]{}
|
||||||
|
_ = Foo[map[rune]byte]{}
|
||||||
|
)
|
||||||
Loading…
Add table
Add a link
Reference in a new issue