[SSI] openssi/kernel/kernel exit.c,1.21,1.22 pid.c,1.9,1.10

Roger Tsang <[email protected]>
Newsgroups gmane.linux.cluster.ssic.cvs
Message-ID <[email protected]>
Update of /cvsroot/ssic-linux/openssi/kernel/kernel
In directory sfp-cvsdas-3.v30.ch3.sourceforge.com:/tmp/cvs-serv23888/kernel

Modified Files:
      Tag: OPENSSI-FC
	exit.c pid.c 
Log Message:
VPROC:
- Fix select_bad_process() NULL p_vproc pointer dereference.
- Fix de_thread() related issues:
  - Fix de_thread() calling VPOP_RECLAIM_CHILD() while holding spin_lock(task->p
roc_lock). Code path might sleep.
  - Fix NULL p_vproc pointer dereference when thread group leader is exiting, ha
s PF_FORKNOEXEC flag, and has lost race with de_thread(). Affects exit_notify(),
 forget_original_parent(), and will_become_orphaned_pgrp(). When p_vproc is NULL
 the exiting process reaps itself.
  - Fix dpvproc_nocldwait_async_handler() NULL pointer dereference due to failed
 lookup for vproc of new parent when lost race with de_thread(). (#ifdef RELEASE
_TASK_LEADER_GONE__VPROC_FIX)
  - New PVPOP_SWITCH_PID() to switch VProc PID of process doing de_thread().
  - New PV_DETHREAD_REAP flag is set during de_thread() to indicate to child rea
per to reap thread group leader without delay.
  - Fix oops in do_notify_resume() path due to NULL pointer dereference. p_vproc
 is NULL after bad fork.

VPROC (#ifdef VPROC_RELEASE__REFCNT_RACE_FIX):
- Fix extra VPROC_RELE() on PVPOP_RMV_PGRP_LIST() -ESRCH error.
- Fix PVPOP_REAP() extra dpvproc_remove_pgrp_leader_member_care() on PVPOP_RMV_P
GRP_LIST() -EBUSY error; was typo in if-test.
- PVPOP_REAP() no longer does async PVPOP_RMV_PGRP_LIST(); now sync. Don't see h
ow reaping parent can hold PGRP LOCK in PVPOP_REAP() path.
- Fix exit_vproc() did not decrement vproc reference for process group leader on
 member node. This is in do_fork() error path.

VPROC (#ifdef VPROC_CONTINUE):
- Fix dpvproc_nocldwait_async_handler() deadlock on PVPOP_REAP() -EBUSY due to d
elay_group_leader(). PV_REAPER_RETRY flag is set and group leader is re-inserted
 into the queue so that the remaining threads in thread group can be reaped by t
his handler to remove the delay_group_leader() condition.
- Regression:
  - Fix pproc_reap() should succeed, but returns -EBUSY when process is a thread
 group leader in non-empty thread group and is already in EXIT_DEAD state.


Index: exit.c
===================================================================
RCS file: /cvsroot/ssic-linux/openssi/kernel/kernel/exit.c,v
retrieving revision 1.21
retrieving revision 1.22
diff -u -d -r1.21 -r1.22
--- exit.c	27 Oct 2009 03:18:30 -0000	1.21
+++ exit.c	17 Dec 2009 05:46:51 -0000	1.22
@@ -244,8 +244,10 @@
 	 */
 	if (ignored_task) {
 		v = ignored_task->p_vproc;
-		BUG_ON(!VP_HASHED(v));
-		(void) VPOP_ADJUST_JOB_CONTROL_COUNT(v);
+		if (v) {
+			BUG_ON(!VP_HASHED(v));
+			(void) VPOP_ADJUST_JOB_CONTROL_COUNT(v);
+		}
 		return 0;
 	}
 
@@ -747,7 +749,8 @@
 
 		/* release lock obtained in exit_notify() - dont reacquire */
 		write_unlock_irq(&tasklist_lock);
-		VPOP_REASSIGN_ORIGINAL_PARENT(father->p_vproc, newppid);
+		if (father->p_vproc)
+			VPOP_REASSIGN_ORIGINAL_PARENT(father->p_vproc, newppid);
 	}
 #else
 	list_for_each_safe(_p, _n, &father->children) {
@@ -904,11 +907,29 @@
 
 
 #ifdef CONFIG_VPROC
-	VPOP_CLEANUP_VPROC_RELATIONS(tsk->p_vproc);
+	/* TODO: Delay VPOP_XXX calls so we can hold
+	 * write_lock_irq(&tasklist_lock) throughout.
+	 */
+	if (tsk->p_vproc) {
+		VPOP_CLEANUP_VPROC_RELATIONS(tsk->p_vproc);
 #ifdef VPROC_PVP_CHILD_LL
-	WARN_ON(!list_empty(&PVP(tsk->p_vproc)->pvp_children));
+		WARN_ON(!list_empty(&PVP(tsk->p_vproc)->pvp_children));
 #endif
-#else
+	} else {
+		SSI_ASSERT(tsk->flags & PF_FORKNOEXEC);
+		tsk->exit_state = EXIT_DEAD;
+
+		/*
+		 * Clear these here so that update_process_times() won't try to deliver
+		 * itimer, profile or rlimit signals to this task while it is in late exit.
+		 */
+		tsk->it_virt_value = cputime_zero;
+		tsk->it_prof_value = cputime_zero;
+
+		/* release it - nobody will wait for it */
+		release_task(tsk);
+	}
+#else /* CONFIG_VPROC */
 	/* If something other than our normal parent is ptracing us, then
 	 * send it a SIGCHLD instead of honoring exit_signal.  exit_signal
 	 * only has special meaning to our real parent.
@@ -1747,11 +1768,26 @@
 	get_task_struct(tsk);
 	do {
 #ifdef TASK_HOLD_VPROC
+#ifdef VPROC_RCU_LIST
+		int retry = 0;
+retry_vproc:
+#endif
 		vp = tsk->p_vproc;
 
 		if (!VPROC_HOLD_AND_CHECK(vp, "do_wait")) {
+#ifdef VPROC_RCU_LIST
+			if (retry) {
+				put_task_struct(tsk);
+				goto next_thread;
+			}
+			/* de_thread() might be re-hashing vproc */
+			retry = 1;
+			idelay(HZ>>4);
+			goto retry_vproc;
+#else
 			put_task_struct(tsk);
 			goto next_thread;
+#endif
 		}
 
 		vrtn = VPOP_WAIT(vp, pid, vopts, stat_addr, &pusage, &vretval);
@@ -2189,24 +2225,43 @@
 	if (security_task_wait(cp))
 		goto out_unlock;
 
+#ifdef VPROC_CONTINUE
+	/* Perform some checks to ensure we don't unnecessarily
+	 * delay reaping the thread group leader.
+	 */
+	if (delayed_group_leader &&
+	    (vopts & VPROC_WZOMBIE)) {
+		/* FIXME: We don't want to reap before VPOP_RECLAIM_CHILD(leader)
+		 * completes in de_thread(). Also if switch_exec_pids() is run then
+		 * delayed_group_leader == 0.
+		 */
+		if (vopts & VPROC_WDETHREAD)
+			delayed_group_leader = 0;
+#if 0
+		/* From exit_notify(), reap self on group exit */
+		else if (cp->exit_signal == -1 &&
+		    (likely(cp->ptrace == 0) ||
+		     unlikely(cp->signal->flags & SIGNAL_GROUP_EXIT)))
+			delayed_group_leader = 0;
+#endif
+	}
+#else
 	if (vopts & VPROC_WZOMBIE) {
-		if (delayed_group_leader) { 
+		if (delayed_group_leader) {
 			/* Cannot be reaped yet, member list not empty yet */
 			retval = -EBUSY;
-#ifndef VPROC_CONTINUE
 			goto out_unlock;
 		}
 		/* Wait for task to finish exiting */
 		WAIT_EVENT(&cp->p_exiting);
-#else
-		}
 #if 0
 		else if (!(vopts & VPROC_WNOWAIT))
 			/* Wait for task to finish exiting */
 			WAIT_EVENT(&cp->p_exiting);
 #endif
-#endif /* VPROC_CONTINUE */
 	}
+#endif /* !VPROC_CONTINUE */
+
 	/*
 	 * Task is ready to be reaped, reap it.
 	 */
@@ -2245,8 +2300,10 @@
 			 * Eligible but we cannot release
 			 * it yet:
 			 */
-			if (delayed_group_leader)
+			if (delayed_group_leader) {
+				retval = -EBUSY;
 				goto check_continued;
+			}
 			retval = wait_task_zombie(cp, (vopts & VPROC_WNOWAIT),
 							NULL,
 							stat_addr, pusagep);

Index: pid.c
===================================================================
RCS file: /cvsroot/ssic-linux/openssi/kernel/kernel/pid.c,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -d -r1.9 -r1.10
--- pid.c	5 Nov 2009 07:33:38 -0000	1.9
+++ pid.c	17 Dec 2009 05:46:51 -0000	1.10
@@ -300,7 +300,7 @@
 	leader->pid = leader->tgid = thread->pid;
 	thread->pid = thread->tgid;
 #ifdef VPROC
-	/* NB: There is no need to switch vproc pids.
+	/* SSI_XXX: No need to switch vproc pids?
 	 * glibc tst-exec4 passes with no stale vproc handles.
 	 */
 #if 0
@@ -326,6 +326,11 @@
 	leader->p_vproc->vp_pid = leader->pid;
 	list_add_rcu(&leader->p_vproc->vp_list, &vproc_hash[VPROCPIDHASH(leader->pid)]);
 	VPROC_LIST_UNLOCK();
+
+	/* Update pvp_pgid so we can get to pgrp list from pvproc */
+	/* SSI_XXX: Locking for pvp_pgid */
+	PVP(thread->p_vproc)->pvp_pgid = leader->pid;
+	PVP(leader->p_vproc)->pvp_pgid = leader->pid;
 #endif
 #endif
 	leader->epid = thread->epid;


------------------------------------------------------------------------------
This SF.Net email is sponsored by the Verizon Developer Community
Take advantage of Verizon's best-in-class app development support
A streamlined, 14 day to market process makes app distribution fast and easy
Join now and get one step closer to millions of Verizon customers
http://p.sf.net/sfu/verizon-dev2dev
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.