1. 18 6月, 2015 1 次提交
  2. 02 6月, 2015 3 次提交
  3. 27 5月, 2015 1 次提交
  4. 19 5月, 2015 2 次提交
    • V
      clockevents: Stop unused clockevent devices · d2540875
      Viresh Kumar 提交于
      To avoid getting spurious interrupts on a tickless CPU, clockevent
      device can now be stopped by switching to ONESHOT_STOPPED state.
      
      The natural place for handling this transition is tick_program_event().
      
      On 'expires == KTIME_MAX', we skip programming the event and so we need
      to fix such call sites as well, to always call tick_program_event()
      irrespective of the expires value.
      
      Once the clockevent device is required again, check if it was earlier
      put into ONESHOT_STOPPED state. If yes, switch its state to ONESHOT
      before programming its event.
      
      To make sure we haven't missed any corner case, add a WARN() for the
      case where we try to reprogram clockevent device while we aren't
      configured in ONESHOT_STOPPED state.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Cc: linaro-kernel@lists.linaro.org
      Cc: Frederic Weisbecker <fweisbec@gmail.com>
      Cc: Kevin Hilman <khilman@linaro.org>
      Cc: Daniel Lezcano <daniel.lezcano@linaro.org>
      Cc: Preeti U Murthy <preeti@linux.vnet.ibm.com>
      Cc: Peter Zijlstra <peterz@infradead.org>
      Link: http://lkml.kernel.org/r/5146b07be7f0bc497e0ebae036590ec2fa73e540.1428031396.git.viresh.kumar@linaro.orgSigned-off-by: NThomas Gleixner <tglx@linutronix.de>
      d2540875
    • V
      clockevents: Introduce CLOCK_EVT_STATE_ONESHOT_STOPPED state · 8fff52fd
      Viresh Kumar 提交于
      When no timers/hrtimers are pending, the expiry time is set to a
      special value: 'KTIME_MAX'. This normally happens with
      NO_HZ_{IDLE|FULL} in both LOWRES/HIGHRES modes.
      
      When 'expiry == KTIME_MAX', we either cancel the 'tick-sched' hrtimer
      (NOHZ_MODE_HIGHRES) or skip reprogramming clockevent device
      (NOHZ_MODE_LOWRES).  But, the clockevent device is already
      reprogrammed from the tick-handler for next tick.
      
      As the clock event device is programmed in ONESHOT mode it will at
      least fire one more time (unnecessarily). Timers on few
      implementations (like arm_arch_timer, etc.) only support PERIODIC mode
      and their drivers emulate ONESHOT over that. Which means that on these
      platforms we will get spurious interrupts periodically (at last
      programmed interval rate, normally tick rate).
      
      In order to avoid spurious interrupts, the clockevent device should be
      stopped or its interrupts should be masked.
      
      A simple (yet hacky) solution to get this fixed could be: update
      hrtimer_force_reprogram() to always reprogram clockevent device and
      update clockevent drivers to STOP generating events (or delay it to
      max time) when 'expires' is set to KTIME_MAX. But the drawback here is
      that every clockevent driver has to be hacked for this particular case
      and its very easy for new ones to miss this.
      
      However, Thomas suggested to add an optional state ONESHOT_STOPPED to
      solve this problem: lkml.org/lkml/2014/5/9/508.
      
      This patch adds support for ONESHOT_STOPPED state in clockevents
      core. It will only be available to drivers that implement the
      state-specific callbacks instead of the legacy ->set_mode() callback.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Reviewed-by: NPreeti U. Murthy <preeti@linux.vnet.ibm.com>
      Cc: linaro-kernel@lists.linaro.org
      Cc: Frederic Weisbecker <fweisbec@gmail.com>
      Cc: Kevin Hilman <khilman@linaro.org>
      Cc: Daniel Lezcano <daniel.lezcano@linaro.org>
      Cc: Peter Zijlstra <peterz@infradead.org>
      Link: http://lkml.kernel.org/r/b8b383a03ac07b13312c16850b5106b82e4245b5.1428031396.git.viresh.kumar@linaro.orgSigned-off-by: NThomas Gleixner <tglx@linutronix.de>
      8fff52fd
  5. 25 4月, 2015 1 次提交
  6. 03 4月, 2015 6 次提交
  7. 01 4月, 2015 3 次提交
  8. 27 3月, 2015 3 次提交
  9. 02 3月, 2015 1 次提交
  10. 18 2月, 2015 1 次提交
    • V
      clockevents: Introduce mode specific callbacks · bd624d75
      Viresh Kumar 提交于
      It is not possible for the clockevents core to know which modes (other than
      those with a corresponding feature flag) are supported by a particular
      implementation. And drivers are expected to handle transition to all modes
      elegantly, as ->set_mode() would be issued for them unconditionally.
      
      Now, adding support for a new mode complicates things a bit if we want to use
      the legacy ->set_mode() callback. We need to closely review all clockevents
      drivers to see if they would break on addition of a new mode. And after such
      reviews, it is found that we have to do non-trivial changes to most of the
      drivers [1].
      
      Introduce mode-specific set_mode_*() callbacks, some of which the drivers may or
      may not implement. A missing callback would clearly convey the message that the
      corresponding mode isn't supported.
      
      A driver may still choose to keep supporting the legacy ->set_mode() callback,
      but ->set_mode() wouldn't be supporting any new modes beyond RESUME. If a driver
      wants to benefit from using a new mode, it would be required to migrate to
      the mode specific callbacks.
      
      The legacy ->set_mode() callback and the newly introduced mode-specific
      callbacks are mutually exclusive. Only one of them should be supported by the
      driver.
      
      Sanity check is done at the time of registration to distinguish between optional
      and required callbacks and to make error recovery and handling simpler. If the
      legacy ->set_mode() callback is provided, all mode specific ones would be
      ignored by the core but a warning is thrown if they are present.
      
      Call sites calling ->set_mode() directly are also updated to use
      __clockevents_set_mode() instead, as ->set_mode() may not be available anymore
      for few drivers.
      
       [1] https://lkml.org/lkml/2014/12/9/605
       [2] https://lkml.org/lkml/2015/1/23/255
      
      Suggested-by: Thomas Gleixner <tglx@linutronix.de> [2]
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Signed-off-by: NPeter Zijlstra (Intel) <peterz@infradead.org>
      Cc: Daniel Lezcano <daniel.lezcano@linaro.org>
      Cc: Frederic Weisbecker <fweisbec@gmail.com>
      Cc: John Stultz <john.stultz@linaro.org>
      Cc: Kevin Hilman <khilman@linaro.org>
      Cc: Linus Torvalds <torvalds@linux-foundation.org>
      Cc: Preeti U Murthy <preeti@linux.vnet.ibm.com>
      Cc: linaro-kernel@lists.linaro.org
      Cc: linaro-networking@linaro.org
      Link: http://lkml.kernel.org/r/792d59a40423f0acffc9bb0bec9de1341a06fa02.1423788565.git.viresh.kumar@linaro.orgSigned-off-by: NIngo Molnar <mingo@kernel.org>
      bd624d75
  11. 25 10月, 2014 1 次提交
  12. 01 8月, 2014 1 次提交
    • J
      timer: Fix lock inversion between hrtimer_bases.lock and scheduler locks · 504d5874
      Jan Kara 提交于
      clockevents_increase_min_delta() calls printk() from under
      hrtimer_bases.lock. That causes lock inversion on scheduler locks because
      printk() can call into the scheduler. Lockdep puts it as:
      
      ======================================================
      [ INFO: possible circular locking dependency detected ]
      3.15.0-rc8-06195-g939f04be #2 Not tainted
      -------------------------------------------------------
      trinity-main/74 is trying to acquire lock:
       (&port_lock_key){-.....}, at: [<811c60be>] serial8250_console_write+0x8c/0x10c
      
      but task is already holding lock:
       (hrtimer_bases.lock){-.-...}, at: [<8103caeb>] hrtimer_try_to_cancel+0x13/0x66
      
      which lock already depends on the new lock.
      
      the existing dependency chain (in reverse order) is:
      
      -> #5 (hrtimer_bases.lock){-.-...}:
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f11d>] _raw_spin_lock_irqsave+0x2e/0x3e
             [<8103c918>] __hrtimer_start_range_ns+0x1c/0x197
             [<8107ec20>] perf_swevent_start_hrtimer.part.41+0x7a/0x85
             [<81080792>] task_clock_event_start+0x3a/0x3f
             [<810807a4>] task_clock_event_add+0xd/0x14
             [<8108259a>] event_sched_in+0xb6/0x17a
             [<810826a2>] group_sched_in+0x44/0x122
             [<81082885>] ctx_sched_in.isra.67+0x105/0x11f
             [<810828e6>] perf_event_sched_in.isra.70+0x47/0x4b
             [<81082bf6>] __perf_install_in_context+0x8b/0xa3
             [<8107eb8e>] remote_function+0x12/0x2a
             [<8105f5af>] smp_call_function_single+0x2d/0x53
             [<8107e17d>] task_function_call+0x30/0x36
             [<8107fb82>] perf_install_in_context+0x87/0xbb
             [<810852c9>] SYSC_perf_event_open+0x5c6/0x701
             [<810856f9>] SyS_perf_event_open+0x17/0x19
             [<8142f8ee>] syscall_call+0x7/0xb
      
      -> #4 (&ctx->lock){......}:
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f04c>] _raw_spin_lock+0x21/0x30
             [<81081df3>] __perf_event_task_sched_out+0x1dc/0x34f
             [<8142cacc>] __schedule+0x4c6/0x4cb
             [<8142cae0>] schedule+0xf/0x11
             [<8142f9a6>] work_resched+0x5/0x30
      
      -> #3 (&rq->lock){-.-.-.}:
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f04c>] _raw_spin_lock+0x21/0x30
             [<81040873>] __task_rq_lock+0x33/0x3a
             [<8104184c>] wake_up_new_task+0x25/0xc2
             [<8102474b>] do_fork+0x15c/0x2a0
             [<810248a9>] kernel_thread+0x1a/0x1f
             [<814232a2>] rest_init+0x1a/0x10e
             [<817af949>] start_kernel+0x303/0x308
             [<817af2ab>] i386_start_kernel+0x79/0x7d
      
      -> #2 (&p->pi_lock){-.-...}:
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f11d>] _raw_spin_lock_irqsave+0x2e/0x3e
             [<810413dd>] try_to_wake_up+0x1d/0xd6
             [<810414cd>] default_wake_function+0xb/0xd
             [<810461f3>] __wake_up_common+0x39/0x59
             [<81046346>] __wake_up+0x29/0x3b
             [<811b8733>] tty_wakeup+0x49/0x51
             [<811c3568>] uart_write_wakeup+0x17/0x19
             [<811c5dc1>] serial8250_tx_chars+0xbc/0xfb
             [<811c5f28>] serial8250_handle_irq+0x54/0x6a
             [<811c5f57>] serial8250_default_handle_irq+0x19/0x1c
             [<811c56d8>] serial8250_interrupt+0x38/0x9e
             [<810510e7>] handle_irq_event_percpu+0x5f/0x1e2
             [<81051296>] handle_irq_event+0x2c/0x43
             [<81052cee>] handle_level_irq+0x57/0x80
             [<81002a72>] handle_irq+0x46/0x5c
             [<810027df>] do_IRQ+0x32/0x89
             [<8143036e>] common_interrupt+0x2e/0x33
             [<8142f23c>] _raw_spin_unlock_irqrestore+0x3f/0x49
             [<811c25a4>] uart_start+0x2d/0x32
             [<811c2c04>] uart_write+0xc7/0xd6
             [<811bc6f6>] n_tty_write+0xb8/0x35e
             [<811b9beb>] tty_write+0x163/0x1e4
             [<811b9cd9>] redirected_tty_write+0x6d/0x75
             [<810b6ed6>] vfs_write+0x75/0xb0
             [<810b7265>] SyS_write+0x44/0x77
             [<8142f8ee>] syscall_call+0x7/0xb
      
      -> #1 (&tty->write_wait){-.....}:
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f11d>] _raw_spin_lock_irqsave+0x2e/0x3e
             [<81046332>] __wake_up+0x15/0x3b
             [<811b8733>] tty_wakeup+0x49/0x51
             [<811c3568>] uart_write_wakeup+0x17/0x19
             [<811c5dc1>] serial8250_tx_chars+0xbc/0xfb
             [<811c5f28>] serial8250_handle_irq+0x54/0x6a
             [<811c5f57>] serial8250_default_handle_irq+0x19/0x1c
             [<811c56d8>] serial8250_interrupt+0x38/0x9e
             [<810510e7>] handle_irq_event_percpu+0x5f/0x1e2
             [<81051296>] handle_irq_event+0x2c/0x43
             [<81052cee>] handle_level_irq+0x57/0x80
             [<81002a72>] handle_irq+0x46/0x5c
             [<810027df>] do_IRQ+0x32/0x89
             [<8143036e>] common_interrupt+0x2e/0x33
             [<8142f23c>] _raw_spin_unlock_irqrestore+0x3f/0x49
             [<811c25a4>] uart_start+0x2d/0x32
             [<811c2c04>] uart_write+0xc7/0xd6
             [<811bc6f6>] n_tty_write+0xb8/0x35e
             [<811b9beb>] tty_write+0x163/0x1e4
             [<811b9cd9>] redirected_tty_write+0x6d/0x75
             [<810b6ed6>] vfs_write+0x75/0xb0
             [<810b7265>] SyS_write+0x44/0x77
             [<8142f8ee>] syscall_call+0x7/0xb
      
      -> #0 (&port_lock_key){-.....}:
             [<8104a62d>] __lock_acquire+0x9ea/0xc6d
             [<8104a942>] lock_acquire+0x92/0x101
             [<8142f11d>] _raw_spin_lock_irqsave+0x2e/0x3e
             [<811c60be>] serial8250_console_write+0x8c/0x10c
             [<8104e402>] call_console_drivers.constprop.31+0x87/0x118
             [<8104f5d5>] console_unlock+0x1d7/0x398
             [<8104fb70>] vprintk_emit+0x3da/0x3e4
             [<81425f76>] printk+0x17/0x19
             [<8105bfa0>] clockevents_program_min_delta+0x104/0x116
             [<8105c548>] clockevents_program_event+0xe7/0xf3
             [<8105cc1c>] tick_program_event+0x1e/0x23
             [<8103c43c>] hrtimer_force_reprogram+0x88/0x8f
             [<8103c49e>] __remove_hrtimer+0x5b/0x79
             [<8103cb21>] hrtimer_try_to_cancel+0x49/0x66
             [<8103cb4b>] hrtimer_cancel+0xd/0x18
             [<8107f102>] perf_swevent_cancel_hrtimer.part.60+0x2b/0x30
             [<81080705>] task_clock_event_stop+0x20/0x64
             [<81080756>] task_clock_event_del+0xd/0xf
             [<81081350>] event_sched_out+0xab/0x11e
             [<810813e0>] group_sched_out+0x1d/0x66
             [<81081682>] ctx_sched_out+0xaf/0xbf
             [<81081e04>] __perf_event_task_sched_out+0x1ed/0x34f
             [<8142cacc>] __schedule+0x4c6/0x4cb
             [<8142cae0>] schedule+0xf/0x11
             [<8142f9a6>] work_resched+0x5/0x30
      
      other info that might help us debug this:
      
      Chain exists of:
        &port_lock_key --> &ctx->lock --> hrtimer_bases.lock
      
       Possible unsafe locking scenario:
      
             CPU0                    CPU1
             ----                    ----
        lock(hrtimer_bases.lock);
                                     lock(&ctx->lock);
                                     lock(hrtimer_bases.lock);
        lock(&port_lock_key);
      
       *** DEADLOCK ***
      
      4 locks held by trinity-main/74:
       #0:  (&rq->lock){-.-.-.}, at: [<8142c6f3>] __schedule+0xed/0x4cb
       #1:  (&ctx->lock){......}, at: [<81081df3>] __perf_event_task_sched_out+0x1dc/0x34f
       #2:  (hrtimer_bases.lock){-.-...}, at: [<8103caeb>] hrtimer_try_to_cancel+0x13/0x66
       #3:  (console_lock){+.+...}, at: [<8104fb5d>] vprintk_emit+0x3c7/0x3e4
      
      stack backtrace:
      CPU: 0 PID: 74 Comm: trinity-main Not tainted 3.15.0-rc8-06195-g939f04be #2
       00000000 81c3a310 8b995c14 81426f69 8b995c44 81425a99 8161f671 8161f570
       8161f538 8161f559 8161f538 8b995c78 8b142bb0 00000004 8b142fdc 8b142bb0
       8b995ca8 8104a62d 8b142fac 000016f2 81c3a310 00000001 00000001 00000003
      Call Trace:
       [<81426f69>] dump_stack+0x16/0x18
       [<81425a99>] print_circular_bug+0x18f/0x19c
       [<8104a62d>] __lock_acquire+0x9ea/0xc6d
       [<8104a942>] lock_acquire+0x92/0x101
       [<811c60be>] ? serial8250_console_write+0x8c/0x10c
       [<811c6032>] ? wait_for_xmitr+0x76/0x76
       [<8142f11d>] _raw_spin_lock_irqsave+0x2e/0x3e
       [<811c60be>] ? serial8250_console_write+0x8c/0x10c
       [<811c60be>] serial8250_console_write+0x8c/0x10c
       [<8104af87>] ? lock_release+0x191/0x223
       [<811c6032>] ? wait_for_xmitr+0x76/0x76
       [<8104e402>] call_console_drivers.constprop.31+0x87/0x118
       [<8104f5d5>] console_unlock+0x1d7/0x398
       [<8104fb70>] vprintk_emit+0x3da/0x3e4
       [<81425f76>] printk+0x17/0x19
       [<8105bfa0>] clockevents_program_min_delta+0x104/0x116
       [<8105cc1c>] tick_program_event+0x1e/0x23
       [<8103c43c>] hrtimer_force_reprogram+0x88/0x8f
       [<8103c49e>] __remove_hrtimer+0x5b/0x79
       [<8103cb21>] hrtimer_try_to_cancel+0x49/0x66
       [<8103cb4b>] hrtimer_cancel+0xd/0x18
       [<8107f102>] perf_swevent_cancel_hrtimer.part.60+0x2b/0x30
       [<81080705>] task_clock_event_stop+0x20/0x64
       [<81080756>] task_clock_event_del+0xd/0xf
       [<81081350>] event_sched_out+0xab/0x11e
       [<810813e0>] group_sched_out+0x1d/0x66
       [<81081682>] ctx_sched_out+0xaf/0xbf
       [<81081e04>] __perf_event_task_sched_out+0x1ed/0x34f
       [<8104416d>] ? __dequeue_entity+0x23/0x27
       [<81044505>] ? pick_next_task_fair+0xb1/0x120
       [<8142cacc>] __schedule+0x4c6/0x4cb
       [<81047574>] ? trace_hardirqs_off_caller+0xd7/0x108
       [<810475b0>] ? trace_hardirqs_off+0xb/0xd
       [<81056346>] ? rcu_irq_exit+0x64/0x77
      
      Fix the problem by using printk_deferred() which does not call into the
      scheduler.
      Reported-by: NFengguang Wu <fengguang.wu@intel.com>
      Signed-off-by: NJan Kara <jack@suse.cz>
      Cc: stable@vger.kernel.org
      Signed-off-by: NThomas Gleixner <tglx@linutronix.de>
      504d5874
  13. 07 2月, 2014 3 次提交
  14. 23 10月, 2013 1 次提交
    • T
      clockevents: Sanitize ticks to nsec conversion · 97b94106
      Thomas Gleixner 提交于
      Marc Kleine-Budde pointed out, that commit 77cc982f "clocksource: use
      clockevents_config_and_register() where possible" caused a regression
      for some of the converted subarchs.
      
      The reason is, that the clockevents core code converts the minimal
      hardware tick delta to a nanosecond value for core internal
      usage. This conversion is affected by integer math rounding loss, so
      the backwards conversion to hardware ticks will likely result in a
      value which is less than the configured hardware limitation. The
      affected subarchs used their own workaround (SIGH!) which got lost in
      the conversion.
      
      The solution for the issue at hand is simple: adding evt->mult - 1 to
      the shifted value before the integer divison in the core conversion
      function takes care of it. But this only works for the case where for
      the scaled math mult/shift pair "mult <= 1 << shift" is true. For the
      case where "mult > 1 << shift" we can apply the rounding add only for
      the minimum delta value to make sure that the backward conversion is
      not less than the given hardware limit. For the upper bound we need to
      omit the rounding add, because the backwards conversion is always
      larger than the original latch value. That would violate the upper
      bound of the hardware device.
      
      Though looking closer at the details of that function reveals another
      bogosity: The upper bounds check is broken as well. Checking for a
      resulting "clc" value greater than KTIME_MAX after the conversion is
      pointless. The conversion does:
      
            u64 clc = (latch << evt->shift) / evt->mult;
      
      So there is no sanity check for (latch << evt->shift) exceeding the
      64bit boundary. The latch argument is "unsigned long", so on a 64bit
      arch the handed in argument could easily lead to an unnoticed shift
      overflow. With the above rounding fix applied the calculation before
      the divison is:
      
             u64 clc = (latch << evt->shift) + evt->mult - 1;
      
      So we need to make sure, that neither the shift nor the rounding add
      is overflowing the u64 boundary.
      
      [ukl: move assignment to rnd after eventually changing mult, fix build
       issue and correct comment with the right math]
      Signed-off-by: NThomas Gleixner <tglx@linutronix.de>
      Cc: Russell King - ARM Linux <linux@arm.linux.org.uk>
      Cc: Marc Kleine-Budde <mkl@pengutronix.de>
      Cc: nicolas.ferre@atmel.com
      Cc: Marc Pignat <marc.pignat@hevs.ch>
      Cc: john.stultz@linaro.org
      Cc: kernel@pengutronix.de
      Cc: Ronald Wahl <ronald.wahl@raritan.com>
      Cc: LAK <linux-arm-kernel@lists.infradead.org>
      Cc: Ludovic Desroches <ludovic.desroches@atmel.com>
      Cc: stable@vger.kernel.org
      Link: http://lkml.kernel.org/r/1380052223-24139-1-git-send-email-u.kleine-koenig@pengutronix.deSigned-off-by: NUwe Kleine-König <u.kleine-koenig@pengutronix.de>
      97b94106
  15. 19 10月, 2013 1 次提交
  16. 16 5月, 2013 5 次提交
  17. 15 1月, 2013 1 次提交
  18. 04 9月, 2012 1 次提交
    • R
      timekeeping: Add suspend and resume of clock event devices · adc78e6b
      Rafael J. Wysocki 提交于
      Some clock event devices, for example such that belong to PM domains,
      need to be handled in a spcial way during the timekeeping suspend
      and resume (which takes place in the system core, or "syscore",
      stages of system power transitions) in analogy with clock sources.
      
      Introduce .suspend() and .resume() callbacks for clock event devices
      that will be executed by timekeeping_suspend/_resume(), respectively,
      next the the clock sources' .suspend() and .resume() callbacks.
      Signed-off-by: NRafael J. Wysocki <rjw@sisk.pl>
      adc78e6b
  19. 25 5月, 2012 1 次提交
  20. 31 12月, 2011 1 次提交
  21. 22 12月, 2011 1 次提交
  22. 02 12月, 2011 1 次提交