1
0
mirror of https://github.com/golang/go synced 2024-11-21 23:34:42 -07:00

cmd/compile: fix ICE when compiling global a, b = f()

CL 327651 rewrites a, b = f() to use temporaries when types are not
identical. That would leave OAS2 node appears in body of init function
for global variables initialization. The staticinit pass is not updated
to handle OAS2 node, causing ICE when compiling global variables.

To fix this, handle OAS2 nodes like other OAS2*, since they mostly
necessitate dynamic execution anyway.

Fixes #68264

Change-Id: I1eff8cc3e47035738a2c70d3169e35ec36ee9242
Reviewed-on: https://go-review.googlesource.com/c/go/+/596055
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Auto-Submit: Cuong Manh Le <cuong.manhle.vn@gmail.com>
This commit is contained in:
Cuong Manh Le 2024-07-02 17:17:39 +07:00 committed by Gopher Robot
parent 82c14346d8
commit be152920b9
2 changed files with 29 additions and 0 deletions

View File

@ -107,6 +107,20 @@ func (s *Schedule) tryStaticInit(n ir.Node) bool {
case ir.OAS:
n := n.(*ir.AssignStmt)
lhs, rhs = []ir.Node{n.X}, n.Y
case ir.OAS2:
// Usually OAS2 has been rewritten to separate OASes by types2.
// What's left here is "var a, b = tmp1, tmp2" as a result from rewriting
// "var a, b = f()" that needs type conversion, which is not static.
n := n.(*ir.AssignListStmt)
for _, rhs := range n.Rhs {
for rhs.Op() == ir.OCONVNOP {
rhs = rhs.(*ir.ConvExpr).X
}
if name, ok := rhs.(*ir.Name); !ok || !name.AutoTemp() {
base.FatalfAt(n.Pos(), "unexpected rhs, not an autotmp: %+v", rhs)
}
}
return false
case ir.OAS2DOTTYPE, ir.OAS2FUNC, ir.OAS2MAPR, ir.OAS2RECV:
n := n.(*ir.AssignListStmt)
if len(n.Lhs) < 2 || len(n.Rhs) != 1 {

View File

@ -0,0 +1,15 @@
// compile
// Copyright 2024 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 nat []int
var a, b nat = y()
func y() (nat, []int) {
return nat{0}, nat{1}
}