mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-08-26 10:49:33 +00:00
Merge branch 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/davej/cpufreq
* 'fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/davej/cpufreq: [CPUFREQ] powernow-k8: Limit Pstate transition latency check [CPUFREQ] Fix PCC driver error path [CPUFREQ] fix double freeing in error path of pcc-cpufreq [CPUFREQ] pcc driver should check for pcch method before calling _OSC [CPUFREQ] fix memory leak in cpufreq_add_dev [CPUFREQ] revert "[CPUFREQ] remove rwsem lock from CPUFREQ_GOV_STOP call (second call site)"
This commit is contained in:
commit
ee13cbdec4
3 changed files with 27 additions and 37 deletions
|
@ -368,22 +368,16 @@ static int __init pcc_cpufreq_do_osc(acpi_handle *handle)
|
|||
return -ENODEV;
|
||||
|
||||
out_obj = output.pointer;
|
||||
if (out_obj->type != ACPI_TYPE_BUFFER) {
|
||||
ret = -ENODEV;
|
||||
goto out_free;
|
||||
}
|
||||
if (out_obj->type != ACPI_TYPE_BUFFER)
|
||||
return -ENODEV;
|
||||
|
||||
errors = *((u32 *)out_obj->buffer.pointer) & ~(1 << 0);
|
||||
if (errors) {
|
||||
ret = -ENODEV;
|
||||
goto out_free;
|
||||
}
|
||||
if (errors)
|
||||
return -ENODEV;
|
||||
|
||||
supported = *((u32 *)(out_obj->buffer.pointer + 4));
|
||||
if (!(supported & 0x1)) {
|
||||
ret = -ENODEV;
|
||||
goto out_free;
|
||||
}
|
||||
if (!(supported & 0x1))
|
||||
return -ENODEV;
|
||||
|
||||
out_free:
|
||||
kfree(output.pointer);
|
||||
|
@ -397,13 +391,17 @@ static int __init pcc_cpufreq_probe(void)
|
|||
struct pcc_memory_resource *mem_resource;
|
||||
struct pcc_register_resource *reg_resource;
|
||||
union acpi_object *out_obj, *member;
|
||||
acpi_handle handle, osc_handle;
|
||||
acpi_handle handle, osc_handle, pcch_handle;
|
||||
int ret = 0;
|
||||
|
||||
status = acpi_get_handle(NULL, "\\_SB", &handle);
|
||||
if (ACPI_FAILURE(status))
|
||||
return -ENODEV;
|
||||
|
||||
status = acpi_get_handle(handle, "PCCH", &pcch_handle);
|
||||
if (ACPI_FAILURE(status))
|
||||
return -ENODEV;
|
||||
|
||||
status = acpi_get_handle(handle, "_OSC", &osc_handle);
|
||||
if (ACPI_SUCCESS(status)) {
|
||||
ret = pcc_cpufreq_do_osc(&osc_handle);
|
||||
|
@ -543,13 +541,13 @@ static int pcc_cpufreq_cpu_init(struct cpufreq_policy *policy)
|
|||
|
||||
if (!pcch_virt_addr) {
|
||||
result = -1;
|
||||
goto pcch_null;
|
||||
goto out;
|
||||
}
|
||||
|
||||
result = pcc_get_offset(cpu);
|
||||
if (result) {
|
||||
dprintk("init: PCCP evaluation failed\n");
|
||||
goto free;
|
||||
goto out;
|
||||
}
|
||||
|
||||
policy->max = policy->cpuinfo.max_freq =
|
||||
|
@ -558,14 +556,15 @@ static int pcc_cpufreq_cpu_init(struct cpufreq_policy *policy)
|
|||
ioread32(&pcch_hdr->minimum_frequency) * 1000;
|
||||
policy->cur = pcc_get_freq(cpu);
|
||||
|
||||
if (!policy->cur) {
|
||||
dprintk("init: Unable to get current CPU frequency\n");
|
||||
result = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
|
||||
dprintk("init: policy->max is %d, policy->min is %d\n",
|
||||
policy->max, policy->min);
|
||||
|
||||
return 0;
|
||||
free:
|
||||
pcc_clear_mapping();
|
||||
free_percpu(pcc_cpu_info);
|
||||
pcch_null:
|
||||
out:
|
||||
return result;
|
||||
}
|
||||
|
||||
|
|
|
@ -1023,13 +1023,12 @@ static int get_transition_latency(struct powernow_k8_data *data)
|
|||
}
|
||||
if (max_latency == 0) {
|
||||
/*
|
||||
* Fam 11h always returns 0 as transition latency.
|
||||
* This is intended and means "very fast". While cpufreq core
|
||||
* and governors currently can handle that gracefully, better
|
||||
* set it to 1 to avoid problems in the future.
|
||||
* For all others it's a BIOS bug.
|
||||
* Fam 11h and later may return 0 as transition latency. This
|
||||
* is intended and means "very fast". While cpufreq core and
|
||||
* governors currently can handle that gracefully, better set it
|
||||
* to 1 to avoid problems in the future.
|
||||
*/
|
||||
if (boot_cpu_data.x86 != 0x11)
|
||||
if (boot_cpu_data.x86 < 0x11)
|
||||
printk(KERN_ERR FW_WARN PFX "Invalid zero transition "
|
||||
"latency\n");
|
||||
max_latency = 1;
|
||||
|
|
|
@ -1077,6 +1077,7 @@ static int cpufreq_add_dev(struct sys_device *sys_dev)
|
|||
|
||||
err_unlock_policy:
|
||||
unlock_policy_rwsem_write(cpu);
|
||||
free_cpumask_var(policy->related_cpus);
|
||||
err_free_cpumask:
|
||||
free_cpumask_var(policy->cpus);
|
||||
err_free_policy:
|
||||
|
@ -1762,17 +1763,8 @@ static int __cpufreq_set_policy(struct cpufreq_policy *data,
|
|||
dprintk("governor switch\n");
|
||||
|
||||
/* end old governor */
|
||||
if (data->governor) {
|
||||
/*
|
||||
* Need to release the rwsem around governor
|
||||
* stop due to lock dependency between
|
||||
* cancel_delayed_work_sync and the read lock
|
||||
* taken in the delayed work handler.
|
||||
*/
|
||||
unlock_policy_rwsem_write(data->cpu);
|
||||
if (data->governor)
|
||||
__cpufreq_governor(data, CPUFREQ_GOV_STOP);
|
||||
lock_policy_rwsem_write(data->cpu);
|
||||
}
|
||||
|
||||
/* start new governor */
|
||||
data->governor = policy->governor;
|
||||
|
|
Loading…
Reference in a new issue