. processes stay ZOMBIE, even after wait(), to avoid wrongly seeing them

as living processes  before they are cleaned up (fixes
  wait()/waitpid() hanging forever on previously-ZOMBIE processes)

. stop processes from running using sys_nice() with PRIO_STOP
  when a handled signal is delivered, before computing 
  stack locations for sys_sigsend(). (fixes race condition
  when runnable processes get signals, and e.g. get scheduled
  before FS sends a reply to unpause(), which can make the
  signal stack location wrong.)
This commit is contained in:
Ben Gras 2006-10-25 11:29:43 +00:00
parent 4933f34715
commit 1e656b349d
4 changed files with 10 additions and 3 deletions

View File

@ -326,6 +326,7 @@ int for_trace;
rmp->mp_parent = INIT_PROC_NR;
parent_waiting = mproc[INIT_PROC_NR].mp_flags & WAITING;
if (parent_waiting && (rmp->mp_flags & ZOMBIE) &&
!(rmp->mp_flags & TOLD_PARENT) &&
rmp->mp_fs_call != PM_EXIT) {
cleanup(rmp);
}
@ -369,6 +370,7 @@ PUBLIC int do_waitpid()
/* The value of pidarg determines which children qualify. */
if (pidarg > 0 && pidarg != rp->mp_pid) continue;
if (pidarg < -1 && -pidarg != rp->mp_procgrp) continue;
if (rp->mp_flags & TOLD_PARENT) continue; /* post-ZOMBIE */
children++; /* this child is acceptable */
if (rp->mp_flags & ZOMBIE) {
@ -430,6 +432,8 @@ register struct mproc *child; /* tells which process is exiting */
mp_parent= child->mp_parent;
if (mp_parent <= 0)
panic(__FILE__, "tell_parent: bad value in mp_parent", mp_parent);
if(child->mp_flags & TOLD_PARENT)
panic(__FILE__, "tell_parent: telling parent again", NO_NUM);
parent = &mproc[mp_parent];
/* Wake up the parent by sending the reply message. */
@ -437,7 +441,7 @@ register struct mproc *child; /* tells which process is exiting */
parent->mp_reply.reply_res2 = exitstatus;
setreply(child->mp_parent, child->mp_pid);
parent->mp_flags &= ~WAITING; /* parent no longer waiting */
child->mp_flags &= ~ZOMBIE; /* avoid informing parent twice */
child->mp_flags |= TOLD_PARENT; /* avoid informing parent twice */
}
/*===========================================================================*

View File

@ -794,7 +794,7 @@ message *m_ptr;
/* Clean up if the parent has collected the exit
* status
*/
if (!(rmp->mp_flags & ZOMBIE))
if (rmp->mp_flags & TOLD_PARENT)
real_cleanup(rmp);
break;
@ -909,7 +909,7 @@ message *m_ptr;
/* Clean up if the parent has collected the exit
* status
*/
if (!(rmp->mp_flags & ZOMBIE))
if (rmp->mp_flags & TOLD_PARENT)
real_cleanup(rmp);
break;

View File

@ -84,6 +84,7 @@ EXTERN struct mproc {
#define PRIV_PROC 0x2000 /* system process, special privileges */
#define PM_SIG_PENDING 0x4000 /* process got a signal while waiting for FS */
#define PARTIAL_EXEC 0x8000 /* Process got a new map but no content */
#define TOLD_PARENT 0x10000 /* Parent wait() completed, ZOMBIE off */
#define NIL_MPROC ((struct mproc *) 0)

View File

@ -454,6 +454,8 @@ int signo; /* signal to send to process (1 to _NSIG) */
#endif
sigflags = rmp->mp_sigact[signo].sa_flags;
if (sigismember(&rmp->mp_catch, signo)) {
/* Stop process from running before we do stack calculations. */
sys_nice(rmp->mp_endpoint, PRIO_STOP);
if (rmp->mp_flags & SIGSUSPENDED)
rmp->mp_sigmsg.sm_mask = rmp->mp_sigmask2;
else