-
Notifications
You must be signed in to change notification settings - Fork 365
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Change-Id: Iecaef8945d848f13b1575bd9d5e31bb07de7c307
- Loading branch information
Showing
56 changed files
with
872 additions
and
312 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,4 +1,4 @@ | ||
/* Copyright (c) 2012-2018, The Linux Foundation. All rights reserved. | ||
/* Copyright (c) 2012-2019, The Linux Foundation. All rights reserved. | ||
* Copyright (C) 2006-2007 Adam Belay <[email protected]> | ||
* Copyright (C) 2009 Intel Corporation | ||
* | ||
|
@@ -109,6 +109,7 @@ static DEFINE_PER_CPU(struct lpm_cpu*, cpu_lpm); | |
static bool suspend_in_progress; | ||
static struct hrtimer lpm_hrtimer; | ||
static DEFINE_PER_CPU(struct hrtimer, histtimer); | ||
static DEFINE_PER_CPU(struct hrtimer, biastimer); | ||
static struct lpm_debug *lpm_debug; | ||
static phys_addr_t lpm_debug_phys; | ||
static const int num_dbg_elements = 0x100; | ||
|
@@ -435,6 +436,34 @@ static void msm_pm_set_timer(uint32_t modified_time_us) | |
hrtimer_start(&lpm_hrtimer, modified_ktime, HRTIMER_MODE_REL_PINNED); | ||
} | ||
|
||
static void biastimer_cancel(void) | ||
{ | ||
unsigned int cpu = raw_smp_processor_id(); | ||
struct hrtimer *cpu_biastimer = &per_cpu(biastimer, cpu); | ||
ktime_t time_rem; | ||
|
||
time_rem = hrtimer_get_remaining(cpu_biastimer); | ||
if (ktime_to_us(time_rem) <= 0) | ||
return; | ||
|
||
hrtimer_try_to_cancel(cpu_biastimer); | ||
} | ||
|
||
static enum hrtimer_restart biastimer_fn(struct hrtimer *h) | ||
{ | ||
return HRTIMER_NORESTART; | ||
} | ||
|
||
static void biastimer_start(uint32_t time_ns) | ||
{ | ||
ktime_t bias_ktime = ns_to_ktime(time_ns); | ||
unsigned int cpu = raw_smp_processor_id(); | ||
struct hrtimer *cpu_biastimer = &per_cpu(biastimer, cpu); | ||
|
||
cpu_biastimer->function = biastimer_fn; | ||
hrtimer_start(cpu_biastimer, bias_ktime, HRTIMER_MODE_REL_PINNED); | ||
} | ||
|
||
static uint64_t lpm_cpuidle_predict(struct cpuidle_device *dev, | ||
struct lpm_cpu *cpu, int *idx_restrict, | ||
uint32_t *idx_restrict_time) | ||
|
@@ -595,15 +624,22 @@ static void clear_predict_history(void) | |
|
||
static void update_history(struct cpuidle_device *dev, int idx); | ||
|
||
static inline bool is_cpu_biased(int cpu) | ||
static inline bool is_cpu_biased(int cpu, uint64_t *bias_time) | ||
{ | ||
u64 now = sched_clock(); | ||
u64 last = sched_get_cpu_last_busy_time(cpu); | ||
u64 diff = 0; | ||
|
||
if (!last) | ||
return false; | ||
|
||
return (now - last) < BIAS_HYST; | ||
diff = now - last; | ||
if (diff < BIAS_HYST) { | ||
*bias_time = BIAS_HYST - diff; | ||
return true; | ||
} | ||
|
||
return false; | ||
} | ||
|
||
static int cpu_power_select(struct cpuidle_device *dev, | ||
|
@@ -623,6 +659,7 @@ static int cpu_power_select(struct cpuidle_device *dev, | |
uint32_t next_wakeup_us = (uint32_t)sleep_us; | ||
uint32_t min_residency, max_residency; | ||
struct power_params *pwr_params; | ||
uint64_t bias_time = 0; | ||
|
||
if ((sleep_disabled && !cpu_isolated(dev->cpu)) || sleep_us < 0) | ||
return best_level; | ||
|
@@ -631,8 +668,10 @@ static int cpu_power_select(struct cpuidle_device *dev, | |
|
||
next_event_us = (uint32_t)(ktime_to_us(get_next_event_time(dev->cpu))); | ||
|
||
if (is_cpu_biased(dev->cpu) && (!cpu_isolated(dev->cpu))) | ||
if (is_cpu_biased(dev->cpu, &bias_time) && (!cpu_isolated(dev->cpu))) { | ||
cpu->bias = bias_time; | ||
goto done_select; | ||
} | ||
|
||
for (i = 0; i < cpu->nlevels; i++) { | ||
bool allow; | ||
|
@@ -1310,6 +1349,8 @@ static bool psci_enter_sleep(struct lpm_cpu *cpu, int idx, bool from_idle) | |
*/ | ||
|
||
if (!idx) { | ||
if (cpu->bias) | ||
biastimer_start(cpu->bias); | ||
stop_critical_timings(); | ||
wfi(); | ||
start_critical_timings(); | ||
|
@@ -1420,6 +1461,10 @@ static int lpm_cpuidle_enter(struct cpuidle_device *dev, | |
histtimer_cancel(); | ||
clusttimer_cancel(); | ||
} | ||
if (cpu->bias) { | ||
biastimer_cancel(); | ||
cpu->bias = 0; | ||
} | ||
local_irq_enable(); | ||
return idx; | ||
} | ||
|
@@ -1723,6 +1768,8 @@ static int lpm_probe(struct platform_device *pdev) | |
for_each_possible_cpu(cpu) { | ||
cpu_histtimer = &per_cpu(histtimer, cpu); | ||
hrtimer_init(cpu_histtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); | ||
cpu_histtimer = &per_cpu(biastimer, cpu); | ||
hrtimer_init(cpu_histtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); | ||
} | ||
|
||
cluster_timer_init(lpm_root_node); | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.