From owner-p4-projects@FreeBSD.ORG Thu Jul 14 19:36:27 2005 Return-Path: X-Original-To: p4-projects@freebsd.org Delivered-To: p4-projects@freebsd.org Received: by hub.freebsd.org (Postfix, from userid 32767) id 9FFC816A420; Thu, 14 Jul 2005 19:36:26 +0000 (GMT) X-Original-To: perforce@freebsd.org Delivered-To: perforce@freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id 7511A16A41C; Thu, 14 Jul 2005 19:36:26 +0000 (GMT) (envelope-from julian@elischer.org) Received: from postoffice.vicor-nb.com (postoffice.vicor.com [69.26.56.52]) by mx1.FreeBSD.org (Postfix) with ESMTP id 250C143D46; Thu, 14 Jul 2005 19:36:26 +0000 (GMT) (envelope-from julian@elischer.org) Received: from localhost (localhost [127.0.0.1]) by postoffice.vicor-nb.com (Postfix) with ESMTP id E48344CE7F3; Thu, 14 Jul 2005 12:36:25 -0700 (PDT) Received: from postoffice.vicor-nb.com ([127.0.0.1]) by localhost (postoffice.vicor-nb.com [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id 92251-07; Thu, 14 Jul 2005 12:36:25 -0700 (PDT) Received: from bigwoop.vicor-nb.com (bigwoop.vicor-nb.com [208.206.78.2]) by postoffice.vicor-nb.com (Postfix) with ESMTP id 50E734CE7F2; Thu, 14 Jul 2005 12:36:25 -0700 (PDT) Received: from [208.206.78.97] (julian.vicor-nb.com [208.206.78.97]) by bigwoop.vicor-nb.com (Postfix) with ESMTP id 3FBA27A403; Thu, 14 Jul 2005 12:36:25 -0700 (PDT) Message-ID: <42D6BEB9.6090207@elischer.org> Date: Thu, 14 Jul 2005 12:36:25 -0700 From: Julian Elischer User-Agent: Mozilla/5.0 (X11; U; FreeBSD i386; en-US; rv:1.7.8) Gecko/20050629 X-Accept-Language: en, hu MIME-Version: 1.0 To: John Baldwin References: <200507141810.j6EIApG6000760@repoman.freebsd.org> In-Reply-To: <200507141810.j6EIApG6000760@repoman.freebsd.org> Content-Type: text/plain; charset=us-ascii; format=flowed Content-Transfer-Encoding: 7bit X-Virus-Scanned: by amavisd-new at postoffice.vicor.com Cc: Perforce Change Reviews Subject: Re: PERFORCE change 80196 for review X-BeenThere: p4-projects@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: p4 projects tree changes List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 14 Jul 2005 19:36:27 -0000 Ouch! I had though that I had covered that, but maybe it got uncovered in a later revision. John Baldwin wrote: >http://perforce.freebsd.org/chv.cgi?CH=80196 > >Change 80196 by jhb@jhb_slimer on 2005/07/14 18:09:51 > > Try to close a race between wait() free'ing the vmspace out from > under the last thread that is still trying to exit. > > Reported by: ps > >Affected files ... > >.. //depot/projects/smpng/sys/kern/kern_exit.c#97 edit > >Differences ... > >==== //depot/projects/smpng/sys/kern/kern_exit.c#97 (text+ko) ==== > >@@ -487,6 +487,9 @@ > */ > cpu_exit(td); > >+ WITNESS_WARN(WARN_PANIC, &proctree_lock.sx_object, >+ "process (pid %d) exiting", p->p_pid); >+ > PROC_LOCK(p); > PROC_LOCK(p->p_pptr); > sx_xunlock(&proctree_lock); >@@ -495,20 +498,16 @@ > * We have to wait until after acquiring all locks before > * changing p_state. We need to avoid all possible context > * switches (including ones from blocking on a mutex) while >- * marked as a zombie. >+ * marked as a zombie. We also have to set the zombie state >+ * before we release the parent process' proc lock to avoid >+ * a lost wakeup. So, we first call wakeup, then we grab the >+ * sched lock, update the state, and release the parent process' >+ * proc lock. > */ >+ wakeup(p->p_pptr); > mtx_lock_spin(&sched_lock); > p->p_state = PRS_ZOMBIE; >- >- critical_enter(); >- mtx_unlock_spin(&sched_lock); >- wakeup(p->p_pptr); >- > PROC_UNLOCK(p->p_pptr); >- WITNESS_WARN(WARN_PANIC, &p->p_mtx.mtx_object, >- "process (pid %d) exiting", p->p_pid); >- mtx_lock_spin(&sched_lock); >- critical_exit(); > > /* Do the same timestamp bookkeeping that mi_switch() would do. */ > binuptime(&new_switchtime); >@@ -626,6 +625,20 @@ > > nfound++; > if (p->p_state == PRS_ZOMBIE) { >+ >+ /* >+ * It is possible that the last thread of this >+ * process is still running on another CPU >+ * in thread_exit() after having dropped the process >+ * lock via PROC_UNLOCK() but before it has completed >+ * cpu_throw(). In that case, the other thread must >+ * still hold sched_lock, so simply by acquiring >+ * sched_lock once we will wait long enough for the >+ * thread to exit in that case. >+ */ >+ mtx_lock_spin(&sched_lock); >+ mtx_unlock_spin(&sched_lock); >+ > td->td_retval[0] = p->p_pid; > if (status) > *status = p->p_xstat; /* convert to int */ > >