]> Cypherpunks repositories - gostls13.git/commitdiff
go/types, types2: adjust Checker.recordCommaOkTypes signature
authorRobert Griesemer <gri@golang.org>
Wed, 22 Mar 2023 00:21:17 +0000 (17:21 -0700)
committerGopher Robot <gobot@golang.org>
Fri, 24 Mar 2023 19:13:38 +0000 (19:13 +0000)
By changing the signature to accept a slice rather than an
array, we can avoid creating the array in the first place.

Functionally, we now also record comma-ok types if the
corresponding assignment was incorrect. But this change
provides more (not less) information through the API and
only so if the program is incorrect in the first place.

Change-Id: I0d629441f2f890a37912171fb26ef0e75827ce23
Reviewed-on: https://go-review.googlesource.com/c/go/+/478218
Auto-Submit: Robert Griesemer <gri@google.com>
Run-TryBot: Robert Griesemer <gri@google.com>
Reviewed-by: Robert Findley <rfindley@google.com>
Reviewed-by: Robert Griesemer <gri@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>

src/cmd/compile/internal/types2/assignments.go
src/cmd/compile/internal/types2/check.go
src/go/types/assignments.go
src/go/types/check.go

index 2eecce94c8e4b8887bcf9a66b82f469074717f4b..c774658a23152951a2f96432ce11aa2be76f168c 100644 (file)
@@ -373,11 +373,9 @@ func (check *Checker) initVars(lhs []*Var, orig_rhs []syntax.Expr, returnStmt sy
        }
 
        if commaOk {
-               var a [2]Type
-               for i := range a {
-                       a[i] = check.initVar(lhs[i], rhs[i], context)
-               }
-               check.recordCommaOkTypes(orig_rhs[0], a)
+               check.initVar(lhs[0], rhs[0], context)
+               check.initVar(lhs[1], rhs[1], context)
+               check.recordCommaOkTypes(orig_rhs[0], rhs)
                return
        }
 
@@ -412,11 +410,9 @@ func (check *Checker) assignVars(lhs, orig_rhs []syntax.Expr) {
        }
 
        if commaOk {
-               var a [2]Type
-               for i := range a {
-                       a[i] = check.assignVar(lhs[i], rhs[i])
-               }
-               check.recordCommaOkTypes(orig_rhs[0], a)
+               check.assignVar(lhs[0], rhs[0])
+               check.assignVar(lhs[1], rhs[1])
+               check.recordCommaOkTypes(orig_rhs[0], rhs)
                return
        }
 
index 33b57c0c2c1e5544334e61951c969f84ca0a1876..0c9e80e014ea77a282bf7fe065a76aa37b1bdc50 100644 (file)
@@ -504,22 +504,27 @@ func (check *Checker) recordBuiltinType(f syntax.Expr, sig *Signature) {
        }
 }
 
-func (check *Checker) recordCommaOkTypes(x syntax.Expr, a [2]Type) {
+// recordCommaOkTypes updates recorded types to reflect that x is used in a commaOk context
+// (and therefore has tuple type).
+func (check *Checker) recordCommaOkTypes(x syntax.Expr, a []*operand) {
        assert(x != nil)
-       if a[0] == nil || a[1] == nil {
+       assert(len(a) == 2)
+       if a[0].mode == invalid {
                return
        }
-       assert(isTyped(a[0]) && isTyped(a[1]) && (isBoolean(a[1]) || a[1] == universeError))
+       t0, t1 := a[0].typ, a[1].typ
+       assert(isTyped(t0) && isTyped(t1) && (isBoolean(t1) || t1 == universeError))
        if m := check.Types; m != nil {
                for {
                        tv := m[x]
                        assert(tv.Type != nil) // should have been recorded already
                        pos := x.Pos()
                        tv.Type = NewTuple(
-                               NewVar(pos, check.pkg, "", a[0]),
-                               NewVar(pos, check.pkg, "", a[1]),
+                               NewVar(pos, check.pkg, "", t0),
+                               NewVar(pos, check.pkg, "", t1),
                        )
                        m[x] = tv
+                       // if x is a parenthesized expression (p.X), update p.X
                        p, _ := x.(*syntax.ParenExpr)
                        if p == nil {
                                break
@@ -535,8 +540,8 @@ func (check *Checker) recordCommaOkTypes(x syntax.Expr, a [2]Type) {
                        assert(tv.Type != nil) // should have been recorded already
                        pos := x.Pos()
                        tv.Type = NewTuple(
-                               NewVar(pos, check.pkg, "", a[0]),
-                               NewVar(pos, check.pkg, "", a[1]),
+                               NewVar(pos, check.pkg, "", t0),
+                               NewVar(pos, check.pkg, "", t1),
                        )
                        x.SetTypeInfo(tv)
                        p, _ := x.(*syntax.ParenExpr)
index 8d12df81a057e739d1f36a00fa377f5fc7e9684e..373b8ec23173a5711486da4b342108aff7bb08c3 100644 (file)
@@ -365,11 +365,9 @@ func (check *Checker) initVars(lhs []*Var, origRHS []ast.Expr, returnStmt ast.St
        }
 
        if commaOk {
-               var a [2]Type
-               for i := range a {
-                       a[i] = check.initVar(lhs[i], rhs[i], context)
-               }
-               check.recordCommaOkTypes(origRHS[0], a)
+               check.initVar(lhs[0], rhs[0], context)
+               check.initVar(lhs[1], rhs[1], context)
+               check.recordCommaOkTypes(origRHS[0], rhs)
                return
        }
 
@@ -394,11 +392,9 @@ func (check *Checker) assignVars(lhs, origRHS []ast.Expr) {
        }
 
        if commaOk {
-               var a [2]Type
-               for i := range a {
-                       a[i] = check.assignVar(lhs[i], rhs[i])
-               }
-               check.recordCommaOkTypes(origRHS[0], a)
+               check.assignVar(lhs[0], rhs[0])
+               check.assignVar(lhs[1], rhs[1])
+               check.recordCommaOkTypes(origRHS[0], rhs)
                return
        }
 
index b862ba57b8c44703ffa6843868f314c65f322c83..83e2995bbc2dd9b1ea39598979480d5179ad8cac 100644 (file)
@@ -478,20 +478,24 @@ func (check *Checker) recordBuiltinType(f ast.Expr, sig *Signature) {
        }
 }
 
-func (check *Checker) recordCommaOkTypes(x ast.Expr, a [2]Type) {
+// recordCommaOkTypes updates recorded types to reflect that x is used in a commaOk context
+// (and therefore has tuple type).
+func (check *Checker) recordCommaOkTypes(x ast.Expr, a []*operand) {
        assert(x != nil)
-       if a[0] == nil || a[1] == nil {
+       assert(len(a) == 2)
+       if a[0].mode == invalid {
                return
        }
-       assert(isTyped(a[0]) && isTyped(a[1]) && (isBoolean(a[1]) || a[1] == universeError))
+       t0, t1 := a[0].typ, a[1].typ
+       assert(isTyped(t0) && isTyped(t1) && (isBoolean(t1) || t1 == universeError))
        if m := check.Types; m != nil {
                for {
                        tv := m[x]
                        assert(tv.Type != nil) // should have been recorded already
                        pos := x.Pos()
                        tv.Type = NewTuple(
-                               NewVar(pos, check.pkg, "", a[0]),
-                               NewVar(pos, check.pkg, "", a[1]),
+                               NewVar(pos, check.pkg, "", t0),
+                               NewVar(pos, check.pkg, "", t1),
                        )
                        m[x] = tv
                        // if x is a parenthesized expression (p.X), update p.X