aboutsummaryrefslogtreecommitdiff
path: root/src/cmd/compile/internal/ssa
diff options
context:
space:
mode:
authorJosh Bleecher Snyder <josharian@gmail.com>2021-03-14 14:24:47 -0700
committerJosh Bleecher Snyder <josharian@gmail.com>2021-04-21 00:53:48 +0000
commitfaa4fa1a6e94fce4f6fa22524a2bece5125213b6 (patch)
treeecd5c4b860564b5b1926725f6ffafcebfac3b3d9 /src/cmd/compile/internal/ssa
parent1c268431f49ee2fc843eac52a0854aea3d02a6e0 (diff)
downloadgo-faa4fa1a6e94fce4f6fa22524a2bece5125213b6.tar.gz
go-faa4fa1a6e94fce4f6fa22524a2bece5125213b6.zip
cmd/compile: allow conversion from slice to array ptr
Panic if the slice is too short. Updates #395 Change-Id: I90f4bff2da5d8f3148ba06d2482084f32b25c29a Reviewed-on: https://go-review.googlesource.com/c/go/+/301650 Trust: Josh Bleecher Snyder <josharian@gmail.com> Run-TryBot: Josh Bleecher Snyder <josharian@gmail.com> Reviewed-by: Matthew Dempsky <mdempsky@google.com>
Diffstat (limited to 'src/cmd/compile/internal/ssa')
-rw-r--r--src/cmd/compile/internal/ssa/expand_calls.go4
-rw-r--r--src/cmd/compile/internal/ssa/gen/dec.rules1
-rw-r--r--src/cmd/compile/internal/ssa/gen/genericOps.go4
-rw-r--r--src/cmd/compile/internal/ssa/op.go4
-rw-r--r--src/cmd/compile/internal/ssa/opGen.go6
-rw-r--r--src/cmd/compile/internal/ssa/rewritedec.go16
6 files changed, 32 insertions, 3 deletions
diff --git a/src/cmd/compile/internal/ssa/expand_calls.go b/src/cmd/compile/internal/ssa/expand_calls.go
index be460457a8..46c2388e7b 100644
--- a/src/cmd/compile/internal/ssa/expand_calls.go
+++ b/src/cmd/compile/internal/ssa/expand_calls.go
@@ -508,7 +508,7 @@ func (x *expandState) rewriteSelect(leaf *Value, selector *Value, offset int64,
ls := x.rewriteSelect(leaf, selector.Args[0], offset, regOffset)
locs = x.splitSlots(ls, ".ptr", 0, x.typs.BytePtr)
- case OpSlicePtr:
+ case OpSlicePtr, OpSlicePtrUnchecked:
w := selector.Args[0]
ls := x.rewriteSelect(leaf, w, offset, regOffset)
locs = x.splitSlots(ls, ".ptr", 0, types.NewPtr(w.Type.Elem()))
@@ -1202,7 +1202,7 @@ func expandCalls(f *Func) {
case OpStructSelect, OpArraySelect,
OpIData, OpITab,
OpStringPtr, OpStringLen,
- OpSlicePtr, OpSliceLen, OpSliceCap,
+ OpSlicePtr, OpSliceLen, OpSliceCap, OpSlicePtrUnchecked,
OpComplexReal, OpComplexImag,
OpInt64Hi, OpInt64Lo:
w := v.Args[0]
diff --git a/src/cmd/compile/internal/ssa/gen/dec.rules b/src/cmd/compile/internal/ssa/gen/dec.rules
index 4c677f8418..b19489870d 100644
--- a/src/cmd/compile/internal/ssa/gen/dec.rules
+++ b/src/cmd/compile/internal/ssa/gen/dec.rules
@@ -56,6 +56,7 @@
(SlicePtr (SliceMake ptr _ _ )) => ptr
(SliceLen (SliceMake _ len _)) => len
(SliceCap (SliceMake _ _ cap)) => cap
+(SlicePtrUnchecked (SliceMake ptr _ _ )) => ptr
(Load <t> ptr mem) && t.IsSlice() =>
(SliceMake
diff --git a/src/cmd/compile/internal/ssa/gen/genericOps.go b/src/cmd/compile/internal/ssa/gen/genericOps.go
index c38d22e07f..9f6664386c 100644
--- a/src/cmd/compile/internal/ssa/gen/genericOps.go
+++ b/src/cmd/compile/internal/ssa/gen/genericOps.go
@@ -479,6 +479,10 @@ var genericOps = []opData{
{name: "SlicePtr", argLength: 1, typ: "BytePtr"}, // ptr(arg0)
{name: "SliceLen", argLength: 1}, // len(arg0)
{name: "SliceCap", argLength: 1}, // cap(arg0)
+ // SlicePtrUnchecked, like SlicePtr, extracts the pointer from a slice.
+ // SlicePtr values are assumed non-nil, because they are guarded by bounds checks.
+ // SlicePtrUnchecked values can be nil.
+ {name: "SlicePtrUnchecked", argLength: 1},
// Complex (part/whole)
{name: "ComplexMake", argLength: 2}, // arg0=real, arg1=imag
diff --git a/src/cmd/compile/internal/ssa/op.go b/src/cmd/compile/internal/ssa/op.go
index b99a7a6646..f09a08abcf 100644
--- a/src/cmd/compile/internal/ssa/op.go
+++ b/src/cmd/compile/internal/ssa/op.go
@@ -469,6 +469,7 @@ const (
BoundsSlice3BU // ... with unsigned high
BoundsSlice3C // 3-arg slicing operation, 0 <= low <= high failed
BoundsSlice3CU // ... with unsigned low
+ BoundsConvert // conversion to array pointer failed
BoundsKindCount
)
@@ -496,7 +497,8 @@ func boundsABI(b int64) int {
case BoundsSlice3Alen,
BoundsSlice3AlenU,
BoundsSlice3Acap,
- BoundsSlice3AcapU:
+ BoundsSlice3AcapU,
+ BoundsConvert:
return 0
case BoundsSliceAlen,
BoundsSliceAlenU,
diff --git a/src/cmd/compile/internal/ssa/opGen.go b/src/cmd/compile/internal/ssa/opGen.go
index 8c753ea2a3..2f56625397 100644
--- a/src/cmd/compile/internal/ssa/opGen.go
+++ b/src/cmd/compile/internal/ssa/opGen.go
@@ -2834,6 +2834,7 @@ const (
OpSlicePtr
OpSliceLen
OpSliceCap
+ OpSlicePtrUnchecked
OpComplexMake
OpComplexReal
OpComplexImag
@@ -35899,6 +35900,11 @@ var opcodeTable = [...]opInfo{
generic: true,
},
{
+ name: "SlicePtrUnchecked",
+ argLen: 1,
+ generic: true,
+ },
+ {
name: "ComplexMake",
argLen: 2,
generic: true,
diff --git a/src/cmd/compile/internal/ssa/rewritedec.go b/src/cmd/compile/internal/ssa/rewritedec.go
index 4b7db60551..2a73a5ddc8 100644
--- a/src/cmd/compile/internal/ssa/rewritedec.go
+++ b/src/cmd/compile/internal/ssa/rewritedec.go
@@ -23,6 +23,8 @@ func rewriteValuedec(v *Value) bool {
return rewriteValuedec_OpSliceLen(v)
case OpSlicePtr:
return rewriteValuedec_OpSlicePtr(v)
+ case OpSlicePtrUnchecked:
+ return rewriteValuedec_OpSlicePtrUnchecked(v)
case OpStore:
return rewriteValuedec_OpStore(v)
case OpStringLen:
@@ -248,6 +250,20 @@ func rewriteValuedec_OpSlicePtr(v *Value) bool {
}
return false
}
+func rewriteValuedec_OpSlicePtrUnchecked(v *Value) bool {
+ v_0 := v.Args[0]
+ // match: (SlicePtrUnchecked (SliceMake ptr _ _ ))
+ // result: ptr
+ for {
+ if v_0.Op != OpSliceMake {
+ break
+ }
+ ptr := v_0.Args[0]
+ v.copyOf(ptr)
+ return true
+ }
+ return false
+}
func rewriteValuedec_OpStore(v *Value) bool {
v_2 := v.Args[2]
v_1 := v.Args[1]