]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/compile/internal/types2: port CL 576975 to types2
authorAlan Donovan <adonovan@google.com>
Mon, 15 Apr 2024 18:50:39 +0000 (14:50 -0400)
committerGopher Robot <gobot@golang.org>
Mon, 15 Apr 2024 19:10:02 +0000 (19:10 +0000)
This CL ports to types2 the (passing) test from CL 576975,
which fixed a bug in go/types.

Updates #66704
Updates #65294

Change-Id: Icdf77e39ed177d9f9ecc435d5125f02f2ee4dd0f
Reviewed-on: https://go-review.googlesource.com/c/go/+/579015
Auto-Submit: Alan Donovan <adonovan@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Robert Findley <rfindley@google.com>
src/cmd/compile/internal/types2/api_test.go
src/cmd/compile/internal/types2/decl.go

index 008a5302abdca4a21998bdf5aae86110579dfe90..cd979815bfd8c9cffff2e0840b0c76e33c2e7e4d 100644 (file)
@@ -2985,3 +2985,28 @@ func TestTooNew(t *testing.T) {
                }
        }
 }
+
+// This is a regression test for #66704.
+func TestUnaliasTooSoonInCycle(t *testing.T) {
+       t.Setenv("GODEBUG", "gotypesalias=1")
+       const src = `package a
+
+var x T[B] // this appears to cause Unalias to be called on B while still Invalid
+
+type T[_ any] struct{}
+type A T[B]
+type B = T[A]
+`
+
+       f := mustParse(src)
+       pkg, err := new(Config).Check("a", []*syntax.File{f}, nil)
+       if err != nil {
+               t.Fatal(err)
+       }
+
+       B := pkg.Scope().Lookup("B")
+       got, want := Unalias(B.Type()).String(), "a.T[a.A]"
+       if got != want {
+               t.Errorf("Unalias(type B = T[A]) = %q, want %q", got, want)
+       }
+}
index ed7784a6b8635d2bdbf4dc64ba316be6e23ce1ea..8bf9c5830742e4736777837dbeb5e3c24f5a4eb8 100644 (file)
@@ -512,6 +512,11 @@ func (check *Checker) typeDecl(obj *TypeName, tdecl *syntax.TypeDecl, def *TypeN
                        // TODO(gri) Should be able to use nil instead of Typ[Invalid] to mark
                        //           the alias as incomplete. Currently this causes problems
                        //           with certain cycles. Investigate.
+                       //
+                       // NOTE(adonovan): to avoid the Invalid being prematurely observed
+                       // by (e.g.) a var whose type is an unfinished cycle,
+                       // Unalias does not memoize if Invalid. Perhaps we should use a
+                       // special sentinel distinct from Invalid.
                        alias := check.newAlias(obj, Typ[Invalid])
                        setDefType(def, alias)