[dev.unified] cmd/compile: make Unified IR always writes concrete type for const exprs

So we don't have to depend on typecheck pass to fixup the concrete
type for some constant expressions. Previously, the problem won't show up,
until CL 418475 sent, which removes an un-necessary type conversion in
"append(a, b...) to help the optimization kicks in.

For #53888

Change-Id: Idaecd38b7abbaa3ad5b00ff3b1fb0fd8bbeb6726
Reviewed-on: https://go-review.googlesource.com/c/go/+/418514
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
This commit is contained in:
Cuong Manh Le 2022-07-20 20:27:58 +07:00
parent ae43bdc3e3
commit 131f981df0
3 changed files with 37 additions and 27 deletions

View file

@ -6,7 +6,6 @@ package noder
import (
"fmt"
"go/constant"
"cmd/compile/internal/base"
"cmd/compile/internal/ir"
@ -53,31 +52,9 @@ func (g *irgen) expr(expr syntax.Expr) ir.Node {
base.Assert(g.exprStmtOK)
// The gc backend expects all expressions to have a concrete type, and
// types2 mostly satisfies this expectation already. But there are a few
// cases where the Go spec doesn't require converting to concrete type,
// and so types2 leaves them untyped. So we need to fix those up here.
typ := tv.Type
if basic, ok := typ.(*types2.Basic); ok && basic.Info()&types2.IsUntyped != 0 {
switch basic.Kind() {
case types2.UntypedNil:
// ok; can appear in type switch case clauses
// TODO(mdempsky): Handle as part of type switches instead?
case types2.UntypedInt, types2.UntypedFloat, types2.UntypedComplex:
// Untyped rhs of non-constant shift, e.g. x << 1.0.
// If we have a constant value, it must be an int >= 0.
if tv.Value != nil {
s := constant.ToInt(tv.Value)
assert(s.Kind() == constant.Int && constant.Sign(s) >= 0)
}
typ = types2.Typ[types2.Uint]
case types2.UntypedBool:
typ = types2.Typ[types2.Bool] // expression in "if" or "for" condition
case types2.UntypedString:
typ = types2.Typ[types2.String] // argument to "append" or "copy" calls
default:
base.FatalfAt(g.pos(expr), "unexpected untyped type: %v", basic)
}
typ := idealType(tv)
if typ == nil {
base.FatalfAt(g.pos(expr), "unexpected untyped type: %v", tv.Type)
}
// Constant expression.