aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorKeith Randall <khr@golang.org>2026-02-25 07:32:42 -0800
committerGopher Robot <gobot@golang.org>2026-02-27 14:43:53 -0800
commitf5479628d36e6cdd63c39784b58fa7241abd3295 (patch)
tree9fa7eaa030bffe73276f30fe5337b1226b6fae5e /src
parent5055a181560b09170a23be81612ee849e47b0a30 (diff)
downloadgo-f5479628d36e6cdd63c39784b58fa7241abd3295.tar.xz
runtime: on android/arm64, don't read outside 16-byte regions
Because MTE might be enforced. Update #59090 Update #27610 Change-Id: Idfaecbf3b7a93c5e371abcace666febfc303de9a Reviewed-on: https://go-review.googlesource.com/c/go/+/749062 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@google.com>
Diffstat (limited to 'src')
-rw-r--r--src/internal/bytealg/indexbyte_arm64.s21
-rw-r--r--src/runtime/string.go5
2 files changed, 25 insertions, 1 deletions
diff --git a/src/internal/bytealg/indexbyte_arm64.s b/src/internal/bytealg/indexbyte_arm64.s
index 92a61a4302..1101122ec0 100644
--- a/src/internal/bytealg/indexbyte_arm64.s
+++ b/src/internal/bytealg/indexbyte_arm64.s
@@ -34,6 +34,9 @@ TEXT ·IndexByteString<ABIInternal>(SB),NOSPLIT,$0-32
// identify exactly which byte has matched.
CBZ R1, fail
+#ifdef GOOS_android
+ ADD R0, R1, R20 // R20 = end of data
+#endif
MOVD R0, R11
// Magic constant 0x40100401 allows us to identify
// which lane matches the requested byte.
@@ -51,7 +54,17 @@ TEXT ·IndexByteString<ABIInternal>(SB),NOSPLIT,$0-32
// Input string is not 32-byte aligned. We calculate the
// syndrome value for the aligned 32 bytes block containing
// the first bytes and mask off the irrelevant part.
+#ifdef GOOS_android
+ // Android requires us to not read outside an aligned 16-byte
+ // region because MTE might be enforced.
+ VLD1.P (R3), [V1.B16]
+ CMP R3, R20
+ BLS 2(PC)
+ VLD1 (R3), [V2.B16]
+ ADD $0x10, R3
+#else
VLD1.P (R3), [V1.B16, V2.B16]
+#endif
SUB $0x20, R9, R4
ADDS R4, R1, R1
VCMEQ V0.B16, V1.B16, V3.B16
@@ -71,7 +84,15 @@ TEXT ·IndexByteString<ABIInternal>(SB),NOSPLIT,$0-32
CBNZ R6, tail
loop:
+#ifdef GOOS_android
+ VLD1.P (R3), [V1.B16]
+ CMP R3, R20
+ BLS 2(PC)
+ VLD1 (R3), [V2.B16]
+ ADD $0x10, R3
+#else
VLD1.P (R3), [V1.B16, V2.B16]
+#endif
SUBS $0x20, R1, R1
VCMEQ V0.B16, V1.B16, V3.B16
VCMEQ V0.B16, V2.B16, V4.B16
diff --git a/src/runtime/string.go b/src/runtime/string.go
index 15b3868cbc..7207f834a8 100644
--- a/src/runtime/string.go
+++ b/src/runtime/string.go
@@ -8,6 +8,7 @@ import (
"internal/abi"
"internal/bytealg"
"internal/goarch"
+ "internal/goos"
"internal/runtime/math"
"internal/runtime/sys"
"internal/strconv"
@@ -505,7 +506,9 @@ func findnull(s *byte) int {
// It must be the minimum page size for any architecture Go
// runs on. It's okay (just a minor performance loss) if the
// actual system page size is larger than this value.
- const pageSize = 4096
+ // For Android, we set the page size to the MTE size, as MTE
+ // might be enforced. See issue 59090.
+ const pageSize = 4096*(1-goos.IsAndroid) + 16*goos.IsAndroid
offset := 0
ptr := unsafe.Pointer(s)