Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

cmd/compile: internal compiler error: found illegal assignment p.F.G -> uint #49242

ALTree opened this issue Oct 30, 2021 · 3 comments

cmd/compile: internal compiler error: found illegal assignment p.F.G -> uint #49242

ALTree opened this issue Oct 30, 2021 · 3 comments
NeedsFix release-blocker


Copy link

@ALTree ALTree commented Oct 30, 2021

$ gotip version
go version devel go1.18-f288526374 Fri Oct 29 04:21:07 2021 +0000 linux/amd64
package p

func F[G interface{ uint }]() int {
	f := func(uint) int { return 0 }
	return f(G(1))
$ gotip tool compile crash.go 

crash.go:5:12: internal compiler error: found illegal assignment p.F.G -> uint; 

goroutine 1 [running]:
	/home/alberto/go/src/runtime/debug/stack.go:24 +0x65
cmd/compile/internal/base.FatalfAt({0x0?, 0x0?}, {0xd271dd, 0x27}, {0xc0000ccd90, 0x3, 0x3})
	/home/alberto/go/src/cmd/compile/internal/base/print.go:227 +0x1ca
cmd/compile/internal/noder.assignconvfn({0xe7e678, 0xc00031e240}, 0xc000366540)
	/home/alberto/go/src/cmd/compile/internal/noder/transform.go:423 +0x1b2
cmd/compile/internal/noder.typecheckaste(0xd0?, {0xc00031e2d0?, 0xcd7660?}, 0x0, 0xc0000cceb8?, {0xc00009edb0, 0x1, 0x0?})
	/home/alberto/go/src/cmd/compile/internal/noder/transform.go:499 +0x179
	/home/alberto/go/src/cmd/compile/internal/noder/transform.go:160 +0x196

Tentatively labeling this as a release blocker since it's a compiler crasher on a valid program with typeparameters.

cc @randall77 @danscales

@ALTree ALTree added NeedsInvestigation release-blocker labels Oct 30, 2021
@ALTree ALTree added this to the Go1.18 milestone Oct 30, 2021
Copy link

@danscales danscales commented Oct 31, 2021

@griesemer @findleyr In this example, the types2 typechecker is allowing the G(1) argument of f() to be assigned to its one parameter, which has 'uint' type, without explicit conversion. Is that intentionally allowed, or just something that is happening with the implementation?

G(1) has type typeparam, or possibly (depending on final definitions) the type of the constraint 'interface { uint }'. I don't think there is any current assignability rule that makes it clear that we should be able to assign a type param or 'interface { uint }' to a uint, even though there is only one single underlying type 'uint' in the constraint. But maybe we are intending to add that? (I know obviously there hasn't been time to update the assignability rules fully in the spec.) I guess such a new rule may be implied by a bunch of the SingleUnder/Structure implementation work. Just want to be clear on what's allowed or not.

Copy link

@griesemer griesemer commented Oct 31, 2021

I've recently updated checking of assignments and I may have gone a bit too far. So this may (or may not be intended). Will discuss with @ianlancetaylor .

The implementation of the assignability check was too loose. Two named types (defined types, predeclared types, or type parameters) with different names, are not assignable without explicit conversion. This is a bug in the type checker.

That said, this seemingly equivalent program compiles fine:

package p

func _[P int](x P) int {
	return x

func _[P int]() int {
	return P(1)

Fix forthcoming.

@griesemer griesemer self-assigned this Oct 31, 2021
@griesemer griesemer added NeedsFix and removed NeedsInvestigation labels Oct 31, 2021
Copy link

@gopherbot gopherbot commented Oct 31, 2021

Change mentions this issue: cmd/compile/internal/types2: differently named types are not assignable

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
NeedsFix release-blocker
None yet

No branches or pull requests

4 participants