Skip to content

Commit 4d02b12

Browse files
committed
runtime: don't expose stack buffer in stringto{byte,rune}slice
When using a stack-allocated buffer for the result, don't expose the uninitialized portion of it by restricting its capacity to its length. The other option is to zero the portion between len and cap. That seems like more work, but might be worth it if the caller then appends some stuff to the result. But this close to 1.6, I'm inclined to do the simplest fix possible. Fixes #14232 Change-Id: I21c50d3cda02fd2df4d60ba5e2cfe2efe272f333 Reviewed-on: https://go-review.googlesource.com/19231 Reviewed-by: Brad Fitzpatrick <[email protected]> Reviewed-by: Ian Lance Taylor <[email protected]>
1 parent 39304eb commit 4d02b12

File tree

2 files changed

+17
-2
lines changed

2 files changed

+17
-2
lines changed

src/runtime/string.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ func slicebytetostringtmp(b []byte) string {
139139
func stringtoslicebyte(buf *tmpBuf, s string) []byte {
140140
var b []byte
141141
if buf != nil && len(s) <= len(buf) {
142-
b = buf[:len(s)]
142+
b = buf[:len(s):len(s)]
143143
} else {
144144
b = rawbyteslice(len(s))
145145
}
@@ -171,7 +171,7 @@ func stringtoslicerune(buf *[tmpStringBufSize]rune, s string) []rune {
171171
}
172172
var a []rune
173173
if buf != nil && n <= len(buf) {
174-
a = buf[:n]
174+
a = buf[:n:n]
175175
} else {
176176
a = rawruneslice(n)
177177
}

src/runtime/string_test.go

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -222,3 +222,18 @@ func TestRangeStringCast(t *testing.T) {
222222
t.Fatalf("want 0 allocs, got %v", n)
223223
}
224224
}
225+
226+
func TestString2Slice(t *testing.T) {
227+
// Make sure we don't return slices that expose
228+
// an unzeroed section of stack-allocated temp buf
229+
// between len and cap. See issue 14232.
230+
s := "foož"
231+
b := ([]byte)(s)
232+
if cap(b) != 5 {
233+
t.Errorf("want cap of 5, got %d", cap(b))
234+
}
235+
r := ([]rune)(s)
236+
if cap(r) != 4 {
237+
t.Errorf("want cap of 4, got %d", cap(r))
238+
}
239+
}

0 commit comments

Comments
 (0)