From a0841bce6f6fa62d2ff56a02b7566c1d4c08da86 Mon Sep 17 00:00:00 2001 From: davidxu Date: Mon, 29 Sep 2003 06:25:04 +0000 Subject: When concurrency level is reduced and a kse is exiting, make sure no other threads are still referencing the kse by migrating them to initial kse. Reviewed by: deischen --- lib/libkse/thread/thr_kern.c | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'lib/libkse') diff --git a/lib/libkse/thread/thr_kern.c b/lib/libkse/thread/thr_kern.c index 68d533e..167700c 100644 --- a/lib/libkse/thread/thr_kern.c +++ b/lib/libkse/thread/thr_kern.c @@ -1805,6 +1805,7 @@ kse_fini(struct kse *kse) { /* struct kse_group *free_kseg = NULL; */ struct timespec ts; + struct pthread *td; /* * Check to see if this is one of the main kses. @@ -1844,10 +1845,22 @@ kse_fini(struct kse *kse) KSE_SCHED_LOCK(kse, kse->k_kseg); TAILQ_REMOVE(&kse->k_kseg->kg_kseq, kse, k_kgqe); kse->k_kseg->kg_ksecount--; + /* + * Migrate thread to _kse_initial if its lastest + * kse it ran on is the kse. + */ + td = TAILQ_FIRST(&kse->k_kseg->kg_threadq); + while (td != NULL) { + if (td->kse == kse) + td->kse = _kse_initial; + td = TAILQ_NEXT(td, kle); + } KSE_SCHED_UNLOCK(kse, kse->k_kseg); KSE_LOCK_ACQUIRE(kse, &kse_lock); kse_free_unlocked(kse); KSE_LOCK_RELEASE(kse, &kse_lock); + /* Make sure there is always at least one is awake */ + KSE_WAKEUP(_kse_initial); kse_exit(); /* Never returns. */ PANIC("kse_exit() failed for initial kseg"); -- cgit v1.1