Add IPI support for preempting a thread on another CPU.

MFC after:	3 weeks
This commit is contained in:
Stephan Uphoff 2005-06-09 18:23:54 +00:00
parent e912f906d0
commit 6097174e4d
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=147181
6 changed files with 40 additions and 2 deletions

View File

@ -30,6 +30,7 @@ __FBSDID("$FreeBSD$");
#include "opt_cpu.h"
#include "opt_kstack_pages.h"
#include "opt_mp_watchdog.h"
#include "opt_sched.h"
#include <sys/param.h>
#include <sys/systm.h>
@ -956,6 +957,21 @@ ipi_bitmap_handler(struct clockframe frame)
ipi_bitmap = atomic_readandclear_int(&cpu_ipi_pending[cpu]);
#ifdef IPI_PREEMPTION
if (ipi_bitmap & IPI_PREEMPT) {
mtx_lock_spin(&sched_lock);
/* Don't preempt the idle thread */
if (curthread->td_priority < PRI_MIN_IDLE) {
struct thread *running_thread = curthread;
if (running_thread->td_critnest > 1)
running_thread->td_owepreempt = 1;
else
mi_switch(SW_INVOL | SW_PREEMPT, NULL);
}
mtx_unlock_spin(&sched_lock);
}
#endif
/* Nothing to do for AST */
}

View File

@ -123,7 +123,8 @@
/* IPIs handled by IPI_BITMAPED_VECTOR (XXX ups is there a better place?) */
#define IPI_AST 0 /* Generate software trap. */
#define IPI_BITMAP_LAST IPI_AST
#define IPI_PREEMPT 1
#define IPI_BITMAP_LAST IPI_PREEMPT
#define IPI_IS_BITMAPED(x) ((x) <= IPI_BITMAP_LAST)
#define IPI_STOP (APIC_IPI_INTS + 6) /* Stop CPU until restarted. */

View File

@ -216,6 +216,8 @@ options MUTEX_WAKE_ALL
# performance and increase the frequency of kernel panics by
# design. If you aren't sure that you need it then you don't.
# Relies on the PREEMPTION option. DON'T TURN THIS ON.
# IPI_PREEMPTION instructs the kernel to preempt threads running on other
# CPUS if needed. Relies on the PREEMPTION option
# MUTEX_DEBUG enables various extra assertions in the mutex code.
# SLEEPQUEUE_PROFILING enables rudimentary profiling of the hash table
# used to hold active sleep queues.
@ -229,6 +231,7 @@ options MUTEX_WAKE_ALL
# WITNESS_SKIPSPIN disables the witness checks on spin mutexes.
options PREEMPTION
options FULL_PREEMPTION
options IPI_PREEMPTION
options MUTEX_DEBUG
options WITNESS
options WITNESS_KDB

View File

@ -69,6 +69,7 @@ CY_PCI_FASTINTR
DIRECTIO opt_directio.h
FULL_PREEMPTION opt_sched.h
PREEMPTION opt_sched.h
IPI_PREEMPTION opt_sched.h
GEOM_AES opt_geom.h
GEOM_APPLE opt_geom.h
GEOM_BDE opt_geom.h

View File

@ -30,6 +30,7 @@ __FBSDID("$FreeBSD$");
#include "opt_cpu.h"
#include "opt_kstack_pages.h"
#include "opt_mp_watchdog.h"
#include "opt_sched.h"
#if !defined(lint)
#if !defined(SMP)
@ -1178,6 +1179,21 @@ ipi_bitmap_handler(struct clockframe frame)
ipi_bitmap = atomic_readandclear_int(&cpu_ipi_pending[cpu]);
#ifdef IPI_PREEMPTION
if (ipi_bitmap & IPI_PREEMPT) {
mtx_lock_spin(&sched_lock);
/* Don't preempt the idle thread */
if (curthread->td_priority < PRI_MIN_IDLE) {
struct thread *running_thread = curthread;
if (running_thread->td_critnest > 1)
running_thread->td_owepreempt = 1;
else
mi_switch(SW_INVOL | SW_PREEMPT, NULL);
}
mtx_unlock_spin(&sched_lock);
}
#endif
/* Nothing to do for AST */
}

View File

@ -122,7 +122,8 @@
/* IPIs handled by IPI_BITMAPED_VECTOR (XXX ups is there a better place?) */
#define IPI_AST 0 /* Generate software trap. */
#define IPI_BITMAP_LAST IPI_AST
#define IPI_PREEMPT 1
#define IPI_BITMAP_LAST IPI_PREEMPT
#define IPI_IS_BITMAPED(x) ((x) <= IPI_BITMAP_LAST)
#define IPI_STOP (APIC_IPI_INTS + 6) /* Stop CPU until restarted. */