lkml.org 
[lkml]   [2015]   [Apr]   [22]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    Subject[tip:timers/core] hrtimer: Avoid locking in hrtimer_cancel() if timer not active
    Commit-ID:  19d9f4225dd6a47fca430f15eeae345ceb95c301
    Gitweb: http://git.kernel.org/tip/19d9f4225dd6a47fca430f15eeae345ceb95c301
    Author: Thomas Gleixner <tglx@linutronix.de>
    AuthorDate: Tue, 14 Apr 2015 21:09:25 +0000
    Committer: Thomas Gleixner <tglx@linutronix.de>
    CommitDate: Wed, 22 Apr 2015 17:06:52 +0200

    hrtimer: Avoid locking in hrtimer_cancel() if timer not active

    We can do a lockless check for hrtimer_active before actually taking
    the lock in hrtimer[_try_to]_cancel. This is useful for hotpath users
    like nanosleep as they avoid the lock dance when the timer has
    expired.

    This is safe because active is true when the timer is enqueued or the
    callback is running. Taking the hrtimer base lock does not protect
    against concurrent hrtimer_start calls, the callsite has to do the
    proper serialization itself.

    Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
    Acked-by: Peter Zijlstra <peterz@infradead.org>
    Cc: Preeti U Murthy <preeti@linux.vnet.ibm.com>
    Cc: Viresh Kumar <viresh.kumar@linaro.org>
    Cc: Marcelo Tosatti <mtosatti@redhat.com>
    Cc: Frederic Weisbecker <fweisbec@gmail.com>
    Link: http://lkml.kernel.org/r/20150414203503.580273114@linutronix.de
    Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
    ---
    kernel/time/hrtimer.c | 9 +++++++++
    1 file changed, 9 insertions(+)

    diff --git a/kernel/time/hrtimer.c b/kernel/time/hrtimer.c
    index beab02d..3bac942 100644
    --- a/kernel/time/hrtimer.c
    +++ b/kernel/time/hrtimer.c
    @@ -991,6 +991,15 @@ int hrtimer_try_to_cancel(struct hrtimer *timer)
    unsigned long flags;
    int ret = -1;

    + /*
    + * Check lockless first. If the timer is not active (neither
    + * enqueued nor running the callback, nothing to do here. The
    + * base lock does not serialize against a concurrent enqueue,
    + * so we can avoid taking it.
    + */
    + if (!hrtimer_active(timer))
    + return 0;
    +
    base = lock_hrtimer_base(timer, &flags);

    if (!hrtimer_callback_running(timer))

    \
     
     \ /
      Last update: 2015-04-22 21:41    [W:4.031 / U:0.096 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site