diff options
author | julian <julian@FreeBSD.org> | 2007-02-02 05:14:22 +0000 |
---|---|---|
committer | julian <julian@FreeBSD.org> | 2007-02-02 05:14:22 +0000 |
commit | 743211870ffa749e2518186bc1a124f4244a4103 (patch) | |
tree | d55a566fe917af379f08de3f42d1de2b11969791 /sys/kern/sched_4bsd.c | |
parent | c5ea90d4981e736af040adcd080b1d69b9bca24e (diff) | |
download | FreeBSD-src-743211870ffa749e2518186bc1a124f4244a4103.zip FreeBSD-src-743211870ffa749e2518186bc1a124f4244a4103.tar.gz |
Move the seting of the idle_mask bits to a place where they
can't be wrong.
Also use the IDLETD bit in the thread mask to test if its an idle thread
rather than doing a PCPU access.
Diffstat (limited to 'sys/kern/sched_4bsd.c')
-rw-r--r-- | sys/kern/sched_4bsd.c | 42 |
1 files changed, 25 insertions, 17 deletions
diff --git a/sys/kern/sched_4bsd.c b/sys/kern/sched_4bsd.c index 3d795ea..8cbbbbb 100644 --- a/sys/kern/sched_4bsd.c +++ b/sys/kern/sched_4bsd.c @@ -866,9 +866,12 @@ sched_switch(struct thread *td, struct thread *newtd, int flags) * or stopped or any thing else similar. We never put the idle * threads on the run queue, however. */ - if (td == PCPU_GET(idlethread)) + if (td->td_flags & TDF_IDLETD) { TD_SET_CAN_RUN(td); - else { +#ifdef SMP + idle_cpus_mask &= ~PCPU_GET(cpumask); +#endif + } else { if (TD_IS_RUNNING(td)) { /* Put us back on the run queue. */ sched_add(td, (flags & SW_PREEMPT) ? @@ -901,13 +904,33 @@ sched_switch(struct thread *td, struct thread *newtd, int flags) PMC_SWITCH_CONTEXT(td, PMC_FN_CSW_OUT); #endif + /* I feel sleepy */ cpu_switch(td, newtd); + /* + * Where am I? What year is it? + * We are in the same thread that went to sleep above, + * but any amount of time may have passed. All out context + * will still be available as will local variables. + * PCPU values however may have changed as we may have + * changed CPU so don't trust cached values of them. + * New threads will go to fork_exit() instead of here + * so if you change things here you may need to change + * things there too. + * If the thread above was exiting it will never wake + * up again here, so either it has saved everything it + * needed to, or the thread_wait() or wait() will + * need to reap it. + */ #ifdef HWPMC_HOOKS if (PMC_PROC_IS_USING_PMCS(td->td_proc)) PMC_SWITCH_CONTEXT(td, PMC_FN_CSW_IN); #endif } +#ifdef SMP + if (td->td_flags & TDF_IDLETD) + idle_cpus_mask |= PCPU_GET(cpumask); +#endif sched_lock.mtx_lock = (uintptr_t)td; td->td_oncpu = PCPU_GET(cpuid); } @@ -1326,18 +1349,9 @@ sched_idletd(void *dummy) { struct proc *p; struct thread *td; -#ifdef SMP - cpumask_t mycpu; -#endif td = curthread; p = td->td_proc; -#ifdef SMP - mycpu = PCPU_GET(cpumask); - mtx_lock_spin(&sched_lock); - idle_cpus_mask |= mycpu; - mtx_unlock_spin(&sched_lock); -#endif for (;;) { mtx_assert(&Giant, MA_NOTOWNED); @@ -1345,13 +1359,7 @@ sched_idletd(void *dummy) cpu_idle(); mtx_lock_spin(&sched_lock); -#ifdef SMP - idle_cpus_mask &= ~mycpu; -#endif mi_switch(SW_VOL, NULL); -#ifdef SMP - idle_cpus_mask |= mycpu; -#endif mtx_unlock_spin(&sched_lock); } } |