diff options
| author | ArsenySamoylov <samoylov.arseny@gmail.com> | 2026-01-13 13:06:28 +0300 |
|---|---|---|
| committer | Gopher Robot <gobot@golang.org> | 2026-02-02 13:24:26 -0800 |
| commit | 62d08234b797806796af0d51051f2e13caa42e2a (patch) | |
| tree | f37768122ffc5e31fddd6c47548ccf776fd69c92 /src/cmd/compile/internal/walk/expr.go | |
| parent | 35abaf75c35adc9b22038885781b8be70a8476e0 (diff) | |
| download | go-62d08234b797806796af0d51051f2e13caa42e2a.tar.xz | |
internal/maps,cmd/compile/internal/walk: replace calls to mapaccess1* with mapaccess2*
mapaccess1* and mapaccess2* functions share the same implementation and differ only in whether the boolean "found" is returned.
This change replaces mapaccess1* calls with mapaccess2*.
We can do this transparently, since the call site can safely discard the second (boolean) result.
Ideally, mapacces1* functions could be removed entirely, but this change keeps them as thin wrappers for compatibility.
Fixes #73196
Change-Id: I07c3423d22ed1095ac3666d00e134c2747b2f9c1
Reviewed-on: https://go-review.googlesource.com/c/go/+/736020
Reviewed-by: Keith Randall <khr@google.com>
Reviewed-by: Michael Pratt <mpratt@google.com>
Auto-Submit: Keith Randall <khr@golang.org>
LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Keith Randall <khr@golang.org>
Diffstat (limited to 'src/cmd/compile/internal/walk/expr.go')
| -rw-r--r-- | src/cmd/compile/internal/walk/expr.go | 45 |
1 files changed, 34 insertions, 11 deletions
diff --git a/src/cmd/compile/internal/walk/expr.go b/src/cmd/compile/internal/walk/expr.go index 2794671c73..125ffd53b1 100644 --- a/src/cmd/compile/internal/walk/expr.go +++ b/src/cmd/compile/internal/walk/expr.go @@ -868,20 +868,43 @@ func walkIndexMap(n *ir.IndexExpr, init *ir.Nodes) ir.Node { key := mapKeyArg(fast, n, n.Index, n.Assigned) args := []ir.Node{reflectdata.IndexMapRType(base.Pos, n), map_, key} + if n.Assigned { + mapFn := mapfn(mapassign[fast], t, false) + call := mkcall1(mapFn, nil, init, args...) + call.SetType(types.NewPtr(t.Elem())) + call.MarkNonNil() // mapassign always return non-nil pointers. + star := ir.NewStarExpr(base.Pos, call) + star.SetType(t.Elem()) + star.SetTypecheck(1) + return star + } + + // from: + // m[i] + // to: + // var, _ = mapaccess2*(t, m, i) + // *var var mapFn ir.Node - switch { - case n.Assigned: - mapFn = mapfn(mapassign[fast], t, false) - case t.Elem().Size() > abi.ZeroValSize: + if t.Elem().Size() > abi.ZeroValSize { args = append(args, reflectdata.ZeroAddr(t.Elem().Size())) - mapFn = mapfn("mapaccess1_fat", t, true) - default: - mapFn = mapfn(mapaccess1[fast], t, false) + mapFn = mapfn("mapaccess2_fat", t, true) + } else { + mapFn = mapfn(mapaccess[fast], t, false) } - call := mkcall1(mapFn, nil, init, args...) - call.SetType(types.NewPtr(t.Elem())) - call.MarkNonNil() // mapaccess1* and mapassign always return non-nil pointers. - star := ir.NewStarExpr(base.Pos, call) + call := mkcall1(mapFn, mapFn.Type().ResultsTuple(), init, args...) + + var_ := typecheck.TempAt(base.Pos, ir.CurFunc, types.NewPtr(t.Elem())) + var_.SetTypecheck(1) + var_.MarkNonNil() // mapaccess always returns a non-nill pointer + + bool_ := typecheck.TempAt(base.Pos, ir.CurFunc, types.Types[types.TBOOL]) + bool_.SetTypecheck(1) + + r := ir.NewAssignListStmt(base.Pos, ir.OAS2FUNC, []ir.Node{var_, bool_}, []ir.Node{call}) + r.SetTypecheck(1) + init.Append(walkExpr(r, init)) + + star := ir.NewStarExpr(base.Pos, var_) star.SetType(t.Elem()) star.SetTypecheck(1) return star |
