Skip to content

Commit

Permalink
Merge branch 'pm-cpufreq' into pm-opp
Browse files Browse the repository at this point in the history
  • Loading branch information
Rafael J. Wysocki committed Aug 7, 2015
2 parents 19445b2 + 144c8e1 commit 2dc36ec
Show file tree
Hide file tree
Showing 17 changed files with 638 additions and 404 deletions.
12 changes: 12 additions & 0 deletions arch/powerpc/include/asm/opal-api.h
Original file line number Diff line number Diff line change
Expand Up @@ -361,6 +361,7 @@ enum opal_msg_type {
OPAL_MSG_HMI_EVT,
OPAL_MSG_DPO,
OPAL_MSG_PRD,
OPAL_MSG_OCC,
OPAL_MSG_TYPE_MAX,
};

Expand Down Expand Up @@ -700,6 +701,17 @@ struct opal_prd_msg_header {

struct opal_prd_msg;

#define OCC_RESET 0
#define OCC_LOAD 1
#define OCC_THROTTLE 2
#define OCC_MAX_THROTTLE_STATUS 5

struct opal_occ_msg {
__be64 type;
__be64 chip;
__be64 throttle_status;
};

/*
* SG entries
*
Expand Down
4 changes: 1 addition & 3 deletions drivers/acpi/processor_perflib.c
Original file line number Diff line number Diff line change
Expand Up @@ -784,9 +784,7 @@ acpi_processor_register_performance(struct acpi_processor_performance

EXPORT_SYMBOL(acpi_processor_register_performance);

void
acpi_processor_unregister_performance(struct acpi_processor_performance
*performance, unsigned int cpu)
void acpi_processor_unregister_performance(unsigned int cpu)
{
struct acpi_processor *pr;

Expand Down
93 changes: 51 additions & 42 deletions drivers/cpufreq/acpi-cpufreq.c
Original file line number Diff line number Diff line change
Expand Up @@ -65,18 +65,21 @@ enum {
#define MSR_K7_HWCR_CPB_DIS (1ULL << 25)

struct acpi_cpufreq_data {
struct acpi_processor_performance *acpi_data;
struct cpufreq_frequency_table *freq_table;
unsigned int resume;
unsigned int cpu_feature;
unsigned int acpi_perf_cpu;
cpumask_var_t freqdomain_cpus;
};

static DEFINE_PER_CPU(struct acpi_cpufreq_data *, acfreq_data);

/* acpi_perf_data is a pointer to percpu data. */
static struct acpi_processor_performance __percpu *acpi_perf_data;

static inline struct acpi_processor_performance *to_perf_data(struct acpi_cpufreq_data *data)
{
return per_cpu_ptr(acpi_perf_data, data->acpi_perf_cpu);
}

static struct cpufreq_driver acpi_cpufreq_driver;

static unsigned int acpi_pstate_strict;
Expand Down Expand Up @@ -144,7 +147,7 @@ static int _store_boost(int val)

static ssize_t show_freqdomain_cpus(struct cpufreq_policy *policy, char *buf)
{
struct acpi_cpufreq_data *data = per_cpu(acfreq_data, policy->cpu);
struct acpi_cpufreq_data *data = policy->driver_data;

return cpufreq_show_cpus(data->freqdomain_cpus, buf);
}
Expand Down Expand Up @@ -202,7 +205,7 @@ static unsigned extract_io(u32 value, struct acpi_cpufreq_data *data)
struct acpi_processor_performance *perf;
int i;

perf = data->acpi_data;
perf = to_perf_data(data);

for (i = 0; i < perf->state_count; i++) {
if (value == perf->states[i].status)
Expand All @@ -221,7 +224,7 @@ static unsigned extract_msr(u32 msr, struct acpi_cpufreq_data *data)
else
msr &= INTEL_MSR_RANGE;

perf = data->acpi_data;
perf = to_perf_data(data);

cpufreq_for_each_entry(pos, data->freq_table)
if (msr == perf->states[pos->driver_data].status)
Expand Down Expand Up @@ -327,15 +330,16 @@ static void drv_write(struct drv_cmd *cmd)
put_cpu();
}

static u32 get_cur_val(const struct cpumask *mask)
static u32
get_cur_val(const struct cpumask *mask, struct acpi_cpufreq_data *data)
{
struct acpi_processor_performance *perf;
struct drv_cmd cmd;

if (unlikely(cpumask_empty(mask)))
return 0;

switch (per_cpu(acfreq_data, cpumask_first(mask))->cpu_feature) {
switch (data->cpu_feature) {
case SYSTEM_INTEL_MSR_CAPABLE:
cmd.type = SYSTEM_INTEL_MSR_CAPABLE;
cmd.addr.msr.reg = MSR_IA32_PERF_CTL;
Expand All @@ -346,7 +350,7 @@ static u32 get_cur_val(const struct cpumask *mask)
break;
case SYSTEM_IO_CAPABLE:
cmd.type = SYSTEM_IO_CAPABLE;
perf = per_cpu(acfreq_data, cpumask_first(mask))->acpi_data;
perf = to_perf_data(data);
cmd.addr.io.port = perf->control_register.address;
cmd.addr.io.bit_width = perf->control_register.bit_width;
break;
Expand All @@ -364,19 +368,24 @@ static u32 get_cur_val(const struct cpumask *mask)

static unsigned int get_cur_freq_on_cpu(unsigned int cpu)
{
struct acpi_cpufreq_data *data = per_cpu(acfreq_data, cpu);
struct acpi_cpufreq_data *data;
struct cpufreq_policy *policy;
unsigned int freq;
unsigned int cached_freq;

pr_debug("get_cur_freq_on_cpu (%d)\n", cpu);

if (unlikely(data == NULL ||
data->acpi_data == NULL || data->freq_table == NULL)) {
policy = cpufreq_cpu_get(cpu);
if (unlikely(!policy))
return 0;
}

cached_freq = data->freq_table[data->acpi_data->state].frequency;
freq = extract_freq(get_cur_val(cpumask_of(cpu)), data);
data = policy->driver_data;
cpufreq_cpu_put(policy);
if (unlikely(!data || !data->freq_table))
return 0;

cached_freq = data->freq_table[to_perf_data(data)->state].frequency;
freq = extract_freq(get_cur_val(cpumask_of(cpu), data), data);
if (freq != cached_freq) {
/*
* The dreaded BIOS frequency change behind our back.
Expand All @@ -397,7 +406,7 @@ static unsigned int check_freqs(const struct cpumask *mask, unsigned int freq,
unsigned int i;

for (i = 0; i < 100; i++) {
cur_freq = extract_freq(get_cur_val(mask), data);
cur_freq = extract_freq(get_cur_val(mask, data), data);
if (cur_freq == freq)
return 1;
udelay(10);
Expand All @@ -408,18 +417,17 @@ static unsigned int check_freqs(const struct cpumask *mask, unsigned int freq,
static int acpi_cpufreq_target(struct cpufreq_policy *policy,
unsigned int index)
{
struct acpi_cpufreq_data *data = per_cpu(acfreq_data, policy->cpu);
struct acpi_cpufreq_data *data = policy->driver_data;
struct acpi_processor_performance *perf;
struct drv_cmd cmd;
unsigned int next_perf_state = 0; /* Index into perf table */
int result = 0;

if (unlikely(data == NULL ||
data->acpi_data == NULL || data->freq_table == NULL)) {
if (unlikely(data == NULL || data->freq_table == NULL)) {
return -ENODEV;
}

perf = data->acpi_data;
perf = to_perf_data(data);
next_perf_state = data->freq_table[index].driver_data;
if (perf->state == next_perf_state) {
if (unlikely(data->resume)) {
Expand Down Expand Up @@ -482,8 +490,9 @@ static int acpi_cpufreq_target(struct cpufreq_policy *policy,
static unsigned long
acpi_cpufreq_guess_freq(struct acpi_cpufreq_data *data, unsigned int cpu)
{
struct acpi_processor_performance *perf = data->acpi_data;
struct acpi_processor_performance *perf;

perf = to_perf_data(data);
if (cpu_khz) {
/* search the closest match to cpu_khz */
unsigned int i;
Expand Down Expand Up @@ -672,17 +681,17 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy)
goto err_free;
}

data->acpi_data = per_cpu_ptr(acpi_perf_data, cpu);
per_cpu(acfreq_data, cpu) = data;
perf = per_cpu_ptr(acpi_perf_data, cpu);
data->acpi_perf_cpu = cpu;
policy->driver_data = data;

if (cpu_has(c, X86_FEATURE_CONSTANT_TSC))
acpi_cpufreq_driver.flags |= CPUFREQ_CONST_LOOPS;

result = acpi_processor_register_performance(data->acpi_data, cpu);
result = acpi_processor_register_performance(perf, cpu);
if (result)
goto err_free_mask;

perf = data->acpi_data;
policy->shared_type = perf->shared_type;

/*
Expand Down Expand Up @@ -838,26 +847,25 @@ static int acpi_cpufreq_cpu_init(struct cpufreq_policy *policy)
err_freqfree:
kfree(data->freq_table);
err_unreg:
acpi_processor_unregister_performance(perf, cpu);
acpi_processor_unregister_performance(cpu);
err_free_mask:
free_cpumask_var(data->freqdomain_cpus);
err_free:
kfree(data);
per_cpu(acfreq_data, cpu) = NULL;
policy->driver_data = NULL;

return result;
}

static int acpi_cpufreq_cpu_exit(struct cpufreq_policy *policy)
{
struct acpi_cpufreq_data *data = per_cpu(acfreq_data, policy->cpu);
struct acpi_cpufreq_data *data = policy->driver_data;

pr_debug("acpi_cpufreq_cpu_exit\n");

if (data) {
per_cpu(acfreq_data, policy->cpu) = NULL;
acpi_processor_unregister_performance(data->acpi_data,
policy->cpu);
policy->driver_data = NULL;
acpi_processor_unregister_performance(data->acpi_perf_cpu);
free_cpumask_var(data->freqdomain_cpus);
kfree(data->freq_table);
kfree(data);
Expand All @@ -868,7 +876,7 @@ static int acpi_cpufreq_cpu_exit(struct cpufreq_policy *policy)

static int acpi_cpufreq_resume(struct cpufreq_policy *policy)
{
struct acpi_cpufreq_data *data = per_cpu(acfreq_data, policy->cpu);
struct acpi_cpufreq_data *data = policy->driver_data;

pr_debug("acpi_cpufreq_resume\n");

Expand All @@ -880,7 +888,9 @@ static int acpi_cpufreq_resume(struct cpufreq_policy *policy)
static struct freq_attr *acpi_cpufreq_attr[] = {
&cpufreq_freq_attr_scaling_available_freqs,
&freqdomain_cpus,
NULL, /* this is a placeholder for cpb, do not remove */
#ifdef CONFIG_X86_ACPI_CPUFREQ_CPB
&cpb,
#endif
NULL,
};

Expand Down Expand Up @@ -953,17 +963,16 @@ static int __init acpi_cpufreq_init(void)
* only if configured. This is considered legacy code, which
* will probably be removed at some point in the future.
*/
if (check_amd_hwpstate_cpu(0)) {
struct freq_attr **iter;

pr_debug("adding sysfs entry for cpb\n");
if (!check_amd_hwpstate_cpu(0)) {
struct freq_attr **attr;

for (iter = acpi_cpufreq_attr; *iter != NULL; iter++)
;
pr_debug("CPB unsupported, do not expose it\n");

/* make sure there is a terminator behind it */
if (iter[1] == NULL)
*iter = &cpb;
for (attr = acpi_cpufreq_attr; *attr; attr++)
if (*attr == &cpb) {
*attr = NULL;
break;
}
}
#endif
acpi_cpufreq_boost_init();
Expand Down
Loading

0 comments on commit 2dc36ec

Please sign in to comment.