lkml.org 
[lkml]   [2019]   [Jul]   [30]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    Subject[tip:timers/core] hrtimer: Move unmarked hrtimers to soft interrupt expiry on RT
    Commit-ID:  f4f9a0e3f4c01a11043aca77006532c3c889c9ba
    Gitweb: https://git.kernel.org/tip/f4f9a0e3f4c01a11043aca77006532c3c889c9ba
    Author: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
    AuthorDate: Fri, 26 Jul 2019 20:30:57 +0200
    Committer: Thomas Gleixner <tglx@linutronix.de>
    CommitDate: Tue, 30 Jul 2019 23:57:56 +0200

    hrtimer: Move unmarked hrtimers to soft interrupt expiry on RT

    On PREEMPT_RT not all hrtimers can be expired in hard interrupt context
    even if that is perfectly fine on a PREEMPT_RT=n kernel, e.g. because they
    take regular spinlocks. Also for latency reasons PREEMPT_RT tries to defer
    most hrtimers' expiry into softirq context.

    hrtimers marked with HRTIMER_MODE_HARD must be kept in hard interrupt
    context expiry mode. Add the required logic.

    No functional change for PREEMPT_RT=n kernels.

    [ tglx: Split out of a larger combo patch. Added changelog ]

    Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
    Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
    Acked-by: Peter Zijlstra (Intel) <peterz@infradead.org>
    Link: https://lkml.kernel.org/r/20190726185753.551967692@linutronix.de

    ---
    kernel/time/hrtimer.c | 12 +++++++++++-
    1 file changed, 11 insertions(+), 1 deletion(-)

    diff --git a/kernel/time/hrtimer.c b/kernel/time/hrtimer.c
    index 0ace301a56f4..90dcc4d95e91 100644
    --- a/kernel/time/hrtimer.c
    +++ b/kernel/time/hrtimer.c
    @@ -1275,8 +1275,17 @@ static void __hrtimer_init(struct hrtimer *timer, clockid_t clock_id,
    enum hrtimer_mode mode)
    {
    bool softtimer = !!(mode & HRTIMER_MODE_SOFT);
    - int base = softtimer ? HRTIMER_MAX_CLOCK_BASES / 2 : 0;
    struct hrtimer_cpu_base *cpu_base;
    + int base;
    +
    + /*
    + * On PREEMPT_RT enabled kernels hrtimers which are not explicitely
    + * marked for hard interrupt expiry mode are moved into soft
    + * interrupt context for latency reasons and because the callbacks
    + * can invoke functions which might sleep on RT, e.g. spin_lock().
    + */
    + if (IS_ENABLED(CONFIG_PREEMPT_RT) && !(mode & HRTIMER_MODE_HARD))
    + softtimer = true;

    memset(timer, 0, sizeof(struct hrtimer));

    @@ -1290,6 +1299,7 @@ static void __hrtimer_init(struct hrtimer *timer, clockid_t clock_id,
    if (clock_id == CLOCK_REALTIME && mode & HRTIMER_MODE_REL)
    clock_id = CLOCK_MONOTONIC;

    + base = softtimer ? HRTIMER_MAX_CLOCK_BASES / 2 : 0;
    base += hrtimer_clockid_to_base(clock_id);
    timer->is_soft = softtimer;
    timer->is_hard = !softtimer;
    \
     
     \ /
      Last update: 2019-07-31 00:16    [W:4.089 / U:0.108 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site