Two different approaches can be used to reduce the size of kernel
non-preemptable sections: the one used by the Low-Latency patches
(Ingo Molnar and Andrew Morton)[LowLat],
and the one used by the kernel preemptability patch (MontaVista,
TimeSys)[kpreem,
TimeSys].
The preemptable approach, used in most real-time systems,
removes the constraint of a single execution flow inside the
kernel. Thus it is not necessary to disable preemption when an
execution flow enters the kernel. To support full kernel
preemptability, kernel data must be explicitly protected using
mutexes or spinlocks. The Linux preemptable kernel patch,
sponsored by MontaVista, uses this approach and makes the kernel
fully preemptable. Kernel preemption is disabled only when a
spinlock is held.
A similar approach is used by TimeSys, that uses mutexes instead
of spinlocks, and provide priority inheritance. While the MontaVista
patch disables preemption when a spinlock is acquired, the TimeSys
one is based on blocking synchronization.
In a preemptable kernel, the maximum latency is determined by
the maximum amount of time for which a spinlock is held inside
the kernel. Again, it is important to note that BHs are serialized
using a spinlock, thus they contribute to the latency.
An additional patch (lock-breaking) merges some of the low-latency
rescheduling points into the preemptable kernel, for decreasing
the amount of time for which spinlocks are held.