Commit f3e0d143 authored by Martin Möhrmann's avatar Martin Möhrmann

runtime: avoid infinite loop in growslice

On 386 the below code triggered an infinite loop in growslice:
x = make([]byte, 1<<30-1, 1<<30-1)
x = append(x, x...)

Check for overflow when calculating the new slice capacity
and set the new capacity to the requested capacity when an overflow
is detected to avoid an infinite loop.

No automatic test added due to requiring to allocate 1GB of memory
on a 32bit plaform before use of append is able to trigger the
overflow check.

Fixes #21441

Change-Id: Ia871cc9f88479dacf2c7044531b233f83d2fcedf
Reviewed-on: https://go-review.googlesource.com/57950
Run-TryBot: Martin Möhrmann <moehrmann@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: default avatarMarvin Stenger <marvin.stenger94@gmail.com>
Reviewed-by: default avatarKeith Randall <khr@golang.org>
parent f04d5836
......@@ -105,9 +105,16 @@ func growslice(et *_type, old slice, cap int) slice {
if old.len < 1024 {
newcap = doublecap
} else {
for newcap < cap {
// Check 0 < newcap to detect overflow
// and prevent an infinite loop.
for 0 < newcap && newcap < cap {
newcap += newcap / 4
}
// Set newcap to the requested cap when
// the newcap calculation overflowed.
if newcap <= 0 {
newcap = cap
}
}
}
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment