aboutsummaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorJulian Elischer <julian@FreeBSD.org>2002-08-22 21:45:58 +0000
committerJulian Elischer <julian@FreeBSD.org>2002-08-22 21:45:58 +0000
commit49539972e9daccdf4ec5ee14dc7415126efd3ccf (patch)
treea5d47668028d913f63c63c82275b6116ae3b9620 /sys
parent4a6a94d8d803018858d728dad780253f98583be0 (diff)
downloadsrc-49539972e9daccdf4ec5ee14dc7415126efd3ccf.tar.gz
src-49539972e9daccdf4ec5ee14dc7415126efd3ccf.zip
slight cleanup of single-threading code for KSE processes
Notes
Notes: svn path=/head/; revision=102292
Diffstat (limited to 'sys')
-rw-r--r--sys/kern/kern_exec.c16
-rw-r--r--sys/kern/kern_fork.c9
-rw-r--r--sys/kern/kern_kse.c17
-rw-r--r--sys/kern/kern_thread.c17
4 files changed, 53 insertions, 6 deletions
diff --git a/sys/kern/kern_exec.c b/sys/kern/kern_exec.c
index c01f4fa0f30c..02af5eebebd9 100644
--- a/sys/kern/kern_exec.c
+++ b/sys/kern/kern_exec.c
@@ -162,11 +162,19 @@ execve(td, uap)
PROC_LOCK(p);
KASSERT((p->p_flag & P_INEXEC) == 0,
("%s(): process already has P_INEXEC flag", __func__));
- if ((p->p_flag & P_KSES) && thread_single(SNGLE_EXIT)) {
- PROC_UNLOCK(p);
- return (ERESTART); /* Try again later. */
+ if (p->p_flag & P_KSES) {
+ if (thread_single(SNGLE_EXIT)) {
+ PROC_UNLOCK(p);
+ return (ERESTART); /* Try again later. */
+ }
+ /*
+ * If we get here all other threads are dead,
+ * so unset the associated flags and lose KSE mode.
+ */
+ p->p_flag &= ~P_KSES;
+ td->td_flags &= ~TDF_UNBOUND;
+ thread_single_end();
}
- /* If we get here all other threads are dead. */
p->p_flag |= P_INEXEC;
PROC_UNLOCK(p);
diff --git a/sys/kern/kern_fork.c b/sys/kern/kern_fork.c
index e09e98d8df5f..5f9d1bd374d0 100644
--- a/sys/kern/kern_fork.c
+++ b/sys/kern/kern_fork.c
@@ -768,6 +768,15 @@ again:
PROC_UNLOCK(p2);
/*
+ * If other threads are waiting, let them continue now
+ */
+ if (p1->p_flag & P_KSES) {
+ PROC_LOCK(p1);
+ thread_single_end();
+ PROC_UNLOCK(p1);
+ }
+
+ /*
* Return child proc pointer to parent.
*/
*procp = p2;
diff --git a/sys/kern/kern_kse.c b/sys/kern/kern_kse.c
index 664dde45405b..0214237a64a0 100644
--- a/sys/kern/kern_kse.c
+++ b/sys/kern/kern_kse.c
@@ -804,6 +804,21 @@ thread_single_end(void)
PROC_LOCK_ASSERT(p, MA_OWNED);
p->p_flag &= ~P_STOPPED_SNGL;
p->p_singlethread = NULL;
- thread_unsuspend(p);
+ /*
+ * If there are other threads they mey now run,
+ * unless of course there is a blanket 'stop order'
+ * on the process. The single threader must be allowed
+ * to continue however as this is a bad place to stop.
+ */
+ if ((p->p_numthreads != 1) && (!P_SHOULDSTOP(p))) {
+ mtx_lock_spin(&sched_lock);
+ while (( td = TAILQ_FIRST(&p->p_suspended))) {
+ TAILQ_REMOVE(&p->p_suspended, td, td_runq);
+ p->p_suspcount--;
+ setrunqueue(td);
+ }
+ mtx_unlock_spin(&sched_lock);
+ }
}
+
diff --git a/sys/kern/kern_thread.c b/sys/kern/kern_thread.c
index 664dde45405b..0214237a64a0 100644
--- a/sys/kern/kern_thread.c
+++ b/sys/kern/kern_thread.c
@@ -804,6 +804,21 @@ thread_single_end(void)
PROC_LOCK_ASSERT(p, MA_OWNED);
p->p_flag &= ~P_STOPPED_SNGL;
p->p_singlethread = NULL;
- thread_unsuspend(p);
+ /*
+ * If there are other threads they mey now run,
+ * unless of course there is a blanket 'stop order'
+ * on the process. The single threader must be allowed
+ * to continue however as this is a bad place to stop.
+ */
+ if ((p->p_numthreads != 1) && (!P_SHOULDSTOP(p))) {
+ mtx_lock_spin(&sched_lock);
+ while (( td = TAILQ_FIRST(&p->p_suspended))) {
+ TAILQ_REMOVE(&p->p_suspended, td, td_runq);
+ p->p_suspcount--;
+ setrunqueue(td);
+ }
+ mtx_unlock_spin(&sched_lock);
+ }
}
+