mirror of https://github.com/golang/go.git
runtime: fix spurious "[string too long]" error
Maxstring is not updated in the new string routines, this makes runtime think that long strings are bogus. Fixes #8339. LGTM=crawshaw, iant R=golang-codereviews, crawshaw, iant CC=golang-codereviews, khr, rsc https://golang.org/cl/110930043
This commit is contained in:
parent
331bf64d17
commit
97c8b24d01
|
|
@ -6,6 +6,7 @@ package runtime_test
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"runtime"
|
"runtime"
|
||||||
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -122,3 +123,25 @@ func TestStringW(t *testing.T) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestLargeStringConcat(t *testing.T) {
|
||||||
|
output := executeTest(t, largeStringConcatSource, nil)
|
||||||
|
want := "panic: " + strings.Repeat("0", 1<<10) + strings.Repeat("1", 1<<10) +
|
||||||
|
strings.Repeat("2", 1<<10) + strings.Repeat("3", 1<<10)
|
||||||
|
if !strings.HasPrefix(output, want) {
|
||||||
|
t.Fatalf("output does not start with %q:\n%s", want, output)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var largeStringConcatSource = `
|
||||||
|
package main
|
||||||
|
import "strings"
|
||||||
|
func main() {
|
||||||
|
s0 := strings.Repeat("0", 1<<10)
|
||||||
|
s1 := strings.Repeat("1", 1<<10)
|
||||||
|
s2 := strings.Repeat("2", 1<<10)
|
||||||
|
s3 := strings.Repeat("3", 1<<10)
|
||||||
|
s := s0 + s1 + s2 + s3
|
||||||
|
panic(s)
|
||||||
|
}
|
||||||
|
`
|
||||||
|
|
|
||||||
|
|
@ -24,6 +24,7 @@ package runtime
|
||||||
|
|
||||||
#pragma textflag NOSPLIT
|
#pragma textflag NOSPLIT
|
||||||
func rawstring(size intgo) (s String, b Slice) {
|
func rawstring(size intgo) (s String, b Slice) {
|
||||||
|
uintptr ms;
|
||||||
byte *p;
|
byte *p;
|
||||||
|
|
||||||
p = runtime·mallocgc(size, 0, FlagNoScan|FlagNoZero);
|
p = runtime·mallocgc(size, 0, FlagNoScan|FlagNoZero);
|
||||||
|
|
@ -32,6 +33,11 @@ func rawstring(size intgo) (s String, b Slice) {
|
||||||
b.array = p;
|
b.array = p;
|
||||||
b.len = size;
|
b.len = size;
|
||||||
b.cap = size;
|
b.cap = size;
|
||||||
|
for(;;) {
|
||||||
|
ms = runtime·maxstring;
|
||||||
|
if((uintptr)size <= ms || runtime·casp((void**)&runtime·maxstring, (void*)ms, (void*)size))
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#pragma textflag NOSPLIT
|
#pragma textflag NOSPLIT
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue