runtime: fix deadlock detector false negative

The issue was that scvg is assigned *after* the scavenger goroutine is started,
so when the scavenger calls entersyscall() the g==scvg check can fail.
Fixes #5025.

R=golang-dev, iant
CC=golang-dev
https://golang.org/cl/7629045
This commit is contained in:
Dmitriy Vyukov 2013-03-12 17:21:44 +04:00
parent 7f070af515
commit 6ee739d7e9
3 changed files with 10 additions and 9 deletions

View file

@ -409,6 +409,9 @@ runtime·MHeap_Scavenger(void)
bool trace;
Note note, *notep;
g->issystem = true;
g->isbackground = true;
// If we go two minutes without a garbage collection, force one to run.
forcegc = 2*60*1e9;
// If a span goes unused for 5 minutes after a garbage collection,

View file

@ -71,8 +71,6 @@ M* runtime·extram;
int8* runtime·goos;
int32 runtime·ncpu;
static int32 newprocs;
// Keep trace of scavenger's goroutine for deadlock detection.
static G *scvg;
void runtime·mstart(void);
static void runqput(P*, G*);
@ -174,8 +172,7 @@ runtime·main(void)
runtime·lockOSThread();
if(m != &runtime·m0)
runtime·throw("runtime·main not on m0");
scvg = runtime·newproc1(&scavenger, nil, 0, 0, runtime·main);
scvg->issystem = true;
runtime·newproc1(&scavenger, nil, 0, 0, runtime·main);
main·init();
runtime·unlockOSThread();
@ -1265,7 +1262,7 @@ void
p = releasep();
handoffp(p);
if(g == scvg) // do not consider blocked scavenger for deadlock detection
if(g->isbackground) // do not consider blocked scavenger for deadlock detection
inclocked(1);
runtime·gosave(&g->sched); // re-save for traceback
}
@ -1297,7 +1294,7 @@ runtime·exitsyscall(void)
return;
}
if(g == scvg) // do not consider blocked scavenger for deadlock detection
if(g->isbackground) // do not consider blocked scavenger for deadlock detection
inclocked(-1);
// Try to get any other idle P.
m->p = nil;
@ -1899,7 +1896,7 @@ checkdead(void)
}
grunning = 0;
for(gp = runtime·allg; gp; gp = gp->alllink) {
if(gp == scvg)
if(gp->isbackground)
continue;
s = gp->status;
if(s == Gwaiting)

View file

@ -235,8 +235,9 @@ struct G
int8* waitreason; // if status==Gwaiting
G* schedlink;
bool ispanic;
bool issystem;
int8 raceignore; // ignore race detection events
bool issystem; // do not output in stack dump
bool isbackground; // ignore in deadlock detector
int8 raceignore; // ignore race detection events
M* m; // for debuggers, but offset not hard-coded
M* lockedm;
int32 sig;