1
0
mirror of https://github.com/golang/go synced 2024-10-03 06:21:21 -06:00

runtime: make test for freezetheworld more precise

exitsyscallfast checks for freezetheworld, but does so only by
checking if stopwait is positive. This can also happen during
stoptheworld, which is harmless, but confusing. Shortly, it will be
important that we get to the p.status cas even if stopwait is set.

Hence, make this test more specific so it only triggers with
freezetheworld and not other uses of stopwait.

Change-Id: Ibb722cd8360c3ed5a9654482519e3ceb87a8274d
Reviewed-on: https://go-review.googlesource.com/8205
Reviewed-by: Russ Cox <rsc@golang.org>
This commit is contained in:
Austin Clements 2015-03-27 16:11:11 -04:00
parent 253ad67b34
commit 7c37249639

View File

@ -208,6 +208,10 @@ func helpgc(nproc int32) {
unlock(&sched.lock) unlock(&sched.lock)
} }
// freezeStopWait is a large value that freezetheworld sets
// sched.stopwait to in order to request that all Gs permanently stop.
const freezeStopWait = 0x7fffffff
// Similar to stoptheworld but best-effort and can be called several times. // Similar to stoptheworld but best-effort and can be called several times.
// There is no reverse operation, used during crashing. // There is no reverse operation, used during crashing.
// This function must not lock any mutexes. // This function must not lock any mutexes.
@ -220,7 +224,7 @@ func freezetheworld() {
// so try several times // so try several times
for i := 0; i < 5; i++ { for i := 0; i < 5; i++ {
// this should tell the scheduler to not start any new goroutines // this should tell the scheduler to not start any new goroutines
sched.stopwait = 0x7fffffff sched.stopwait = freezeStopWait
atomicstore(&sched.gcwaiting, 1) atomicstore(&sched.gcwaiting, 1)
// this should stop running goroutines // this should stop running goroutines
if !preemptall() { if !preemptall() {
@ -1864,7 +1868,7 @@ func exitsyscallfast() bool {
_g_ := getg() _g_ := getg()
// Freezetheworld sets stopwait but does not retake P's. // Freezetheworld sets stopwait but does not retake P's.
if sched.stopwait != 0 { if sched.stopwait == freezeStopWait {
_g_.m.mcache = nil _g_.m.mcache = nil
_g_.m.p = nil _g_.m.p = nil
return false return false