diff mbox

libgo patch committed: ignore _Gscan bit when checking status in CgocallDone

Message ID CAOyqgcVT9RYnvT6FX3yEOviRrnNYfBccfak42g3AGgG+xP1LcQ@mail.gmail.com
State New
Headers show

Commit Message

Ian Lance Taylor June 12, 2017, 11:14 p.m. UTC
This patch to libgo ignores the _Gscan bit when checking status in
CgocallDone.  It also always access the atomicstatus field atomically.
The effect of not checking the _Gscan bit is that if the GC decides to
scan the stack just as the goroutine is leaving the system call, the
goroutine might fail to call exitsyscall.  Then then typically causes
a runtime assertion failure later on.  If we do call exitsyscall as we
should, it will stall (in casgstatus) until the _Gscan bit is cleared.

Bootstrapped and ran Go testsuite on x86_64-pc-linux-gnu.  Committed
to mainline.

Ian
diff mbox

Patch

Index: gcc/go/gofrontend/MERGE
===================================================================
--- gcc/go/gofrontend/MERGE	(revision 249131)
+++ gcc/go/gofrontend/MERGE	(working copy)
@@ -1,4 +1,4 @@ 
-61222d34c1b33a369bd86008a0541455dd17727e
+908fc7e46ebe36658ed86b65a3d165fccb2e8576
 
 The first line of this file holds the git revision number of the last
 merge done from the gofrontend repository.
Index: libgo/go/runtime/cgo_gccgo.go
===================================================================
--- libgo/go/runtime/cgo_gccgo.go	(revision 249125)
+++ libgo/go/runtime/cgo_gccgo.go	(working copy)
@@ -54,7 +54,7 @@  func CgocallDone() {
 
 	// If we are invoked because the C function called _cgo_panic,
 	// then _cgo_panic will already have exited syscall mode.
-	if gp.atomicstatus == _Gsyscall {
+	if readgstatus(gp)&^_Gscan == _Gsyscall {
 		exitsyscall(0)
 	}
 
Index: libgo/go/runtime/proc.go
===================================================================
--- libgo/go/runtime/proc.go	(revision 249125)
+++ libgo/go/runtime/proc.go	(working copy)
@@ -1459,7 +1459,7 @@  func dropm() {
 
 	// gccgo sets the stack to Gdead here, because the splitstack
 	// context is not initialized.
-	mp.curg.atomicstatus = _Gdead
+	atomic.Store(&mp.curg.atomicstatus, _Gdead)
 	mp.curg.gcstack = nil
 	mp.curg.gcnextsp = nil