diff options
Diffstat (limited to 'kernel/time/tick-sched.c')
-rw-r--r-- | kernel/time/tick-sched.c | 24 |
1 files changed, 14 insertions, 10 deletions
diff --git a/kernel/time/tick-sched.c b/kernel/time/tick-sched.c index 430e1b6901cc..60c9c60e9108 100644 --- a/kernel/time/tick-sched.c +++ b/kernel/time/tick-sched.c | |||
@@ -271,11 +271,11 @@ u64 get_cpu_iowait_time_us(int cpu, u64 *last_update_time) | |||
271 | } | 271 | } |
272 | EXPORT_SYMBOL_GPL(get_cpu_iowait_time_us); | 272 | EXPORT_SYMBOL_GPL(get_cpu_iowait_time_us); |
273 | 273 | ||
274 | static void tick_nohz_stop_sched_tick(struct tick_sched *ts, | 274 | static ktime_t tick_nohz_stop_sched_tick(struct tick_sched *ts, |
275 | ktime_t now, int cpu) | 275 | ktime_t now, int cpu) |
276 | { | 276 | { |
277 | unsigned long seq, last_jiffies, next_jiffies, delta_jiffies; | 277 | unsigned long seq, last_jiffies, next_jiffies, delta_jiffies; |
278 | ktime_t last_update, expires; | 278 | ktime_t last_update, expires, ret = { .tv64 = 0 }; |
279 | struct clock_event_device *dev = __get_cpu_var(tick_cpu_device).evtdev; | 279 | struct clock_event_device *dev = __get_cpu_var(tick_cpu_device).evtdev; |
280 | u64 time_delta; | 280 | u64 time_delta; |
281 | 281 | ||
@@ -358,6 +358,8 @@ static void tick_nohz_stop_sched_tick(struct tick_sched *ts, | |||
358 | if (ts->tick_stopped && ktime_equal(expires, dev->next_event)) | 358 | if (ts->tick_stopped && ktime_equal(expires, dev->next_event)) |
359 | goto out; | 359 | goto out; |
360 | 360 | ||
361 | ret = expires; | ||
362 | |||
361 | /* | 363 | /* |
362 | * nohz_stop_sched_tick can be called several times before | 364 | * nohz_stop_sched_tick can be called several times before |
363 | * the nohz_restart_sched_tick is called. This happens when | 365 | * the nohz_restart_sched_tick is called. This happens when |
@@ -372,11 +374,6 @@ static void tick_nohz_stop_sched_tick(struct tick_sched *ts, | |||
372 | ts->tick_stopped = 1; | 374 | ts->tick_stopped = 1; |
373 | } | 375 | } |
374 | 376 | ||
375 | ts->idle_sleeps++; | ||
376 | |||
377 | /* Mark expires */ | ||
378 | ts->idle_expires = expires; | ||
379 | |||
380 | /* | 377 | /* |
381 | * If the expiration time == KTIME_MAX, then | 378 | * If the expiration time == KTIME_MAX, then |
382 | * in this case we simply stop the tick timer. | 379 | * in this case we simply stop the tick timer. |
@@ -407,6 +404,8 @@ out: | |||
407 | ts->next_jiffies = next_jiffies; | 404 | ts->next_jiffies = next_jiffies; |
408 | ts->last_jiffies = last_jiffies; | 405 | ts->last_jiffies = last_jiffies; |
409 | ts->sleep_length = ktime_sub(dev->next_event, now); | 406 | ts->sleep_length = ktime_sub(dev->next_event, now); |
407 | |||
408 | return ret; | ||
410 | } | 409 | } |
411 | 410 | ||
412 | static bool can_stop_idle_tick(int cpu, struct tick_sched *ts) | 411 | static bool can_stop_idle_tick(int cpu, struct tick_sched *ts) |
@@ -445,7 +444,7 @@ static bool can_stop_idle_tick(int cpu, struct tick_sched *ts) | |||
445 | 444 | ||
446 | static void __tick_nohz_idle_enter(struct tick_sched *ts) | 445 | static void __tick_nohz_idle_enter(struct tick_sched *ts) |
447 | { | 446 | { |
448 | ktime_t now; | 447 | ktime_t now, expires; |
449 | int cpu = smp_processor_id(); | 448 | int cpu = smp_processor_id(); |
450 | 449 | ||
451 | now = tick_nohz_start_idle(cpu, ts); | 450 | now = tick_nohz_start_idle(cpu, ts); |
@@ -454,7 +453,12 @@ static void __tick_nohz_idle_enter(struct tick_sched *ts) | |||
454 | int was_stopped = ts->tick_stopped; | 453 | int was_stopped = ts->tick_stopped; |
455 | 454 | ||
456 | ts->idle_calls++; | 455 | ts->idle_calls++; |
457 | tick_nohz_stop_sched_tick(ts, now, cpu); | 456 | |
457 | expires = tick_nohz_stop_sched_tick(ts, now, cpu); | ||
458 | if (expires.tv64 > 0LL) { | ||
459 | ts->idle_sleeps++; | ||
460 | ts->idle_expires = expires; | ||
461 | } | ||
458 | 462 | ||
459 | if (!was_stopped && ts->tick_stopped) | 463 | if (!was_stopped && ts->tick_stopped) |
460 | ts->idle_jiffies = ts->last_jiffies; | 464 | ts->idle_jiffies = ts->last_jiffies; |