diff options
author | Matthew Dempsky <mdempsky@google.com> | 2022-07-18 13:45:57 -0700 |
---|---|---|
committer | Matthew Dempsky <mdempsky@google.com> | 2022-07-19 23:31:17 +0000 |
commit | 64cd6faa13e9155e7942f3f51127c1d61a38fcf7 (patch) | |
tree | dfbe9fe1de5510440cb302542149ac16965f96fe | |
parent | a4c5198a3c8befa2f126fd365de4dc09c32b7886 (diff) | |
download | go-64cd6faa13e9155e7942f3f51127c1d61a38fcf7.tar.gz go-64cd6faa13e9155e7942f3f51127c1d61a38fcf7.zip |
[dev.unified] cmd/compile/internal/noder: simplify mixed tag/case RTTI wiring
The previous CL largely removed the need for worrying about mixed
tag/case comparisons in switch statements by ensuring they're always
converted to a common type, except for one annoying case: switch
statements with an implicit `true` tag, and case values of interface
type (which must be empty interface, because `bool`'s method set is
empty).
It would be simpler to have writer.go desugar the implicit `true`
itself, because we already handle explicit `true` correctly. But the
existing code already works fine, and I don't want to add further
complexity to writer.go until dictionaries and stenciling is done.
Change-Id: Ia8d44c425b1be7fc578cd570d15a7560fe9d2674
Reviewed-on: https://go-review.googlesource.com/c/go/+/418102
Run-TryBot: Matthew Dempsky <mdempsky@google.com>
Reviewed-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: Keith Randall <khr@golang.org>
-rw-r--r-- | src/cmd/compile/internal/noder/reader.go | 30 |
1 files changed, 14 insertions, 16 deletions
diff --git a/src/cmd/compile/internal/noder/reader.go b/src/cmd/compile/internal/noder/reader.go index 4c90f9dc54..d7ec9f2ebb 100644 --- a/src/cmd/compile/internal/noder/reader.go +++ b/src/cmd/compile/internal/noder/reader.go @@ -1569,23 +1569,21 @@ func (r *reader) switchStmt(label *types.Sym) ir.Node { } else { cases = r.exprList() - tagType := types.Types[types.TBOOL] - if tag != nil { - tagType = tag.Type() - } - for i, cas := range cases { - if cas.Op() == ir.ONIL { - continue // never needs rtype - } - if tagType.IsInterface() != cas.Type().IsInterface() { - typ := tagType - if typ.IsInterface() { - typ = cas.Type() - } - for len(rtypes) < i { - rtypes = append(rtypes, nil) + // For `switch { case any(true): }` (e.g., issue 3980 in + // test/switch.go), the backend still creates a mixed bool/any + // comparison, and we need to explicitly supply the RTTI for the + // comparison. + // + // TODO(mdempsky): Change writer.go to desugar "switch {" into + // "switch true {", which we already handle correctly. + if tag == nil { + for i, cas := range cases { + if cas.Type().IsEmptyInterface() { + for len(rtypes) < i { + rtypes = append(rtypes, nil) + } + rtypes = append(rtypes, reflectdata.TypePtrAt(cas.Pos(), types.Types[types.TBOOL])) } - rtypes = append(rtypes, reflectdata.TypePtrAt(cas.Pos(), typ)) } } } |