mirror of
https://github.com/xen-project/xen.git
synced 2026-10-29 10:40:03 +01:00
Refactor Xen Support for Intel Turbo Boost
Refactor the existing code that supports the Intel Turbo feature to move all the driver specific bits in the cpufreq driver. Create a tri-state interface for the Turbo feature that can distinguish amongst enabled Turbo, disabled Turbo, and processors that don't support Turbo at all. Signed-off-by: Mark Langsdorf <mark.langsdorf@amd.com>
This commit is contained in:
1 parent
e136054ced
commit
002c5bcdbe
10 files changed
+70
-45
No files matched your search
@@ -247,6 +247,7 @@ int xc_get_cpufreq_para(int xc_handle, int cpuid,
|
||||
user_para->scaling_cur_freq = sys_para->scaling_cur_freq;
|
||||
user_para->scaling_max_freq = sys_para->scaling_max_freq;
|
||||
user_para->scaling_min_freq = sys_para->scaling_min_freq;
|
||||
user_para->turbo_enabled = sys_para->turbo_enabled;
|
||||
|
||||
memcpy(user_para->scaling_driver,
|
||||
sys_para->scaling_driver, CPUFREQ_NAME_LEN);
|
||||
|
||||
@@ -1292,6 +1292,8 @@ struct xc_get_cpufreq_para {
|
||||
xc_userspace_t userspace;
|
||||
xc_ondemand_t ondemand;
|
||||
} u;
|
||||
|
||||
int32_t turbo_enabled;
|
||||
};
|
||||
|
||||
int xc_get_cpufreq_para(int xc_handle, int cpuid,
|
||||
|
||||
+14
-4
@@ -30,6 +30,10 @@
|
||||
|
||||
#define ARRAY_SIZE(a) (sizeof (a) / sizeof ((a)[0]))
|
||||
|
||||
#define CPUFREQ_TURBO_DISABLED -1
|
||||
#define CPUFREQ_TURBO_UNSUPPORTED 0
|
||||
#define CPUFREQ_TURBO_ENABLED 1
|
||||
|
||||
static int xc_fd;
|
||||
static int max_cpu_nr;
|
||||
|
||||
@@ -62,8 +66,8 @@ void show_help(void)
|
||||
" set-max-cstate <num> set the C-State limitation (<num> >= 0)\n"
|
||||
" start [seconds] start collect Cx/Px statistics,\n"
|
||||
" output after CTRL-C or SIGINT or several seconds.\n"
|
||||
" enable-turbo-mode [cpuid] enable Turbo Mode in DBS governor.\n"
|
||||
" disable-turbo-mode [cpuid] disable Turbo Mode in DBS governor.\n"
|
||||
" enable-turbo-mode [cpuid] enable Turbo Mode for processors that support it.\n"
|
||||
" disable-turbo-mode [cpuid] disable Turbo Mode for processors that support it.\n"
|
||||
);
|
||||
}
|
||||
/* wrapper function */
|
||||
@@ -529,8 +533,6 @@ static void print_cpufreq_para(int cpuid, struct xc_get_cpufreq_para *p_cpufreq)
|
||||
p_cpufreq->u.ondemand.sampling_rate);
|
||||
printf(" up_threshold : %u\n",
|
||||
p_cpufreq->u.ondemand.up_threshold);
|
||||
printf(" turbo mode : %s\n",
|
||||
p_cpufreq->u.ondemand.turbo_enabled ? "enabled" : "disabled");
|
||||
}
|
||||
|
||||
printf("scaling_avail_freq :");
|
||||
@@ -546,6 +548,13 @@ static void print_cpufreq_para(int cpuid, struct xc_get_cpufreq_para *p_cpufreq)
|
||||
p_cpufreq->scaling_max_freq,
|
||||
p_cpufreq->scaling_min_freq,
|
||||
p_cpufreq->scaling_cur_freq);
|
||||
if (p_cpufreq->turbo_enabled != CPUFREQ_TURBO_UNSUPPORTED) {
|
||||
printf("turbo mode : ");
|
||||
if (p_cpufreq->turbo_enabled == CPUFREQ_TURBO_ENABLED)
|
||||
printf("enabled\n");
|
||||
else
|
||||
printf("disabled\n");
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
@@ -561,6 +570,7 @@ static int show_cpufreq_para_by_cpuid(int xc_fd, int cpuid)
|
||||
p_cpufreq->affected_cpus = NULL;
|
||||
p_cpufreq->scaling_available_frequencies = NULL;
|
||||
p_cpufreq->scaling_available_governors = NULL;
|
||||
p_cpufreq->turbo_enabled = 0;
|
||||
|
||||
do
|
||||
{
|
||||
|
||||
@@ -410,6 +410,10 @@ static int acpi_cpufreq_target(struct cpufreq_policy *policy,
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if (policy->turbo == CPUFREQ_TURBO_DISABLED)
|
||||
if (target_freq > policy->cpuinfo.second_max_freq)
|
||||
target_freq = policy->cpuinfo.second_max_freq;
|
||||
|
||||
perf = data->acpi_data;
|
||||
result = cpufreq_frequency_table_target(policy,
|
||||
data->freq_table,
|
||||
@@ -610,12 +614,19 @@ acpi_cpufreq_cpu_init(struct cpufreq_policy *policy)
|
||||
break;
|
||||
}
|
||||
|
||||
/* Check for APERF/MPERF support in hardware */
|
||||
/* Check for APERF/MPERF support in hardware
|
||||
* also check for boost support */
|
||||
if (c->x86_vendor == X86_VENDOR_INTEL && c->cpuid_level >= 6) {
|
||||
unsigned int ecx;
|
||||
unsigned int eax;
|
||||
ecx = cpuid_ecx(6);
|
||||
if (ecx & CPUID_6_ECX_APERFMPERF_CAPABILITY)
|
||||
acpi_cpufreq_driver.getavg = get_measured_perf;
|
||||
eax = cpuid_eax(6);
|
||||
if ( eax & 0x2 ) {
|
||||
policy->turbo = CPUFREQ_TURBO_ENABLED;
|
||||
printk(XENLOG_INFO "Turbo Mode detected and enabled!\n");
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -299,9 +299,8 @@ static int get_cpufreq_para(struct xen_sysctl_pm_op *op)
|
||||
&op->u.get_para.u.ondemand.sampling_rate_min,
|
||||
&op->u.get_para.u.ondemand.sampling_rate,
|
||||
&op->u.get_para.u.ondemand.up_threshold);
|
||||
op->u.get_para.u.ondemand.turbo_enabled =
|
||||
cpufreq_dbs_get_turbo_status(op->cpuid);
|
||||
}
|
||||
op->u.get_para.turbo_enabled = cpufreq_get_turbo_status(op->cpuid);
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -553,13 +552,13 @@ int do_pm_op(struct xen_sysctl_pm_op *op)
|
||||
|
||||
case XEN_SYSCTL_pm_op_enable_turbo:
|
||||
{
|
||||
cpufreq_dbs_enable_turbo(op->cpuid);
|
||||
cpufreq_enable_turbo(op->cpuid);
|
||||
break;
|
||||
}
|
||||
|
||||
case XEN_SYSCTL_pm_op_disable_turbo:
|
||||
{
|
||||
cpufreq_dbs_disable_turbo(op->cpuid);
|
||||
cpufreq_disable_turbo(op->cpuid);
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
@@ -58,9 +58,6 @@ static struct dbs_tuners {
|
||||
|
||||
static struct timer dbs_timer[NR_CPUS];
|
||||
|
||||
/* Turbo Mode */
|
||||
static int turbo_detected = 0;
|
||||
|
||||
int write_ondemand_sampling_rate(unsigned int sampling_rate)
|
||||
{
|
||||
if ( (sampling_rate > MAX_SAMPLING_RATE / MICROSECS(1)) ||
|
||||
@@ -111,10 +108,6 @@ static void dbs_check_cpu(struct cpu_dbs_info_s *this_dbs_info)
|
||||
|
||||
policy = this_dbs_info->cur_policy;
|
||||
max = policy->max;
|
||||
if (turbo_detected && !this_dbs_info->turbo_enabled) {
|
||||
if (max > policy->cpuinfo.second_max_freq)
|
||||
max = policy->cpuinfo.second_max_freq;
|
||||
}
|
||||
|
||||
if (unlikely(policy->resume)) {
|
||||
__cpufreq_driver_target(policy, max,CPUFREQ_RELATION_H);
|
||||
@@ -276,7 +269,6 @@ int cpufreq_governor_dbs(struct cpufreq_policy *policy, unsigned int event)
|
||||
} else
|
||||
dbs_tuners_ins.sampling_rate = usr_sampling_rate;
|
||||
}
|
||||
this_dbs_info->turbo_enabled = 1;
|
||||
dbs_timer_init(this_dbs_info);
|
||||
|
||||
break;
|
||||
@@ -353,13 +345,6 @@ struct cpufreq_governor cpufreq_gov_dbs = {
|
||||
|
||||
static int __init cpufreq_gov_dbs_init(void)
|
||||
{
|
||||
#ifdef CONFIG_X86
|
||||
unsigned int eax = cpuid_eax(6);
|
||||
if ( eax & 0x2 ) {
|
||||
turbo_detected = 1;
|
||||
printk(XENLOG_INFO "Turbo Mode detected!\n");
|
||||
}
|
||||
#endif
|
||||
return cpufreq_register_governor(&cpufreq_gov_dbs);
|
||||
}
|
||||
__initcall(cpufreq_gov_dbs_init);
|
||||
@@ -404,19 +389,3 @@ void cpufreq_dbs_timer_resume(void)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void cpufreq_dbs_enable_turbo(int cpuid)
|
||||
{
|
||||
per_cpu(cpu_dbs_info, cpuid).turbo_enabled = 1;
|
||||
}
|
||||
|
||||
void cpufreq_dbs_disable_turbo(int cpuid)
|
||||
{
|
||||
per_cpu(cpu_dbs_info, cpuid).turbo_enabled = 0;
|
||||
}
|
||||
|
||||
unsigned int cpufreq_dbs_get_turbo_status(int cpuid)
|
||||
{
|
||||
return turbo_detected && per_cpu(cpu_dbs_info, cpuid).turbo_enabled;
|
||||
}
|
||||
|
||||
@@ -394,6 +394,31 @@ int cpufreq_driver_getavg(unsigned int cpu, unsigned int flag)
|
||||
return policy->cur;
|
||||
}
|
||||
|
||||
void cpufreq_enable_turbo(int cpuid)
|
||||
{
|
||||
struct cpufreq_policy *policy;
|
||||
|
||||
policy = cpufreq_cpu_policy[cpuid];
|
||||
if (policy->turbo != CPUFREQ_TURBO_UNSUPPORTED)
|
||||
policy->turbo = CPUFREQ_TURBO_ENABLED;
|
||||
}
|
||||
|
||||
void cpufreq_disable_turbo(int cpuid)
|
||||
{
|
||||
struct cpufreq_policy *policy;
|
||||
|
||||
policy = cpufreq_cpu_policy[cpuid];
|
||||
if (policy->turbo != CPUFREQ_TURBO_UNSUPPORTED)
|
||||
policy->turbo = CPUFREQ_TURBO_DISABLED;
|
||||
}
|
||||
|
||||
int cpufreq_get_turbo_status(int cpuid)
|
||||
{
|
||||
struct cpufreq_policy *policy;
|
||||
|
||||
policy = cpufreq_cpu_policy[cpuid];
|
||||
return policy->turbo;
|
||||
}
|
||||
|
||||
/*********************************************************************
|
||||
* POLICY *
|
||||
|
||||
@@ -55,6 +55,9 @@ struct cpufreq_policy {
|
||||
|
||||
unsigned int resume; /* flag for cpufreq 1st run
|
||||
* S3 wakeup, hotplug cpu, etc */
|
||||
int turbo; /* tristate flag: 0 for unsupported
|
||||
* -1 for disable, 1 for enabled
|
||||
* See CPUFREQ_TURBO_* below for defines */
|
||||
};
|
||||
extern struct cpufreq_policy *cpufreq_cpu_policy[NR_CPUS];
|
||||
|
||||
@@ -114,6 +117,14 @@ extern int __cpufreq_driver_target(struct cpufreq_policy *policy,
|
||||
#define USR_GETAVG 2
|
||||
extern int cpufreq_driver_getavg(unsigned int cpu, unsigned int flag);
|
||||
|
||||
#define CPUFREQ_TURBO_DISABLED -1
|
||||
#define CPUFREQ_TURBO_UNSUPPORTED 0
|
||||
#define CPUFREQ_TURBO_ENABLED 1
|
||||
|
||||
extern void cpufreq_enable_turbo(int cpuid);
|
||||
extern void cpufreq_disable_turbo(int cpuid);
|
||||
extern int cpufreq_get_turbo_status(int cpuid);
|
||||
|
||||
static __inline__ int
|
||||
__cpufreq_governor(struct cpufreq_policy *policy, unsigned int event)
|
||||
{
|
||||
@@ -241,7 +252,4 @@ int write_userspace_scaling_setspeed(unsigned int cpu, unsigned int freq);
|
||||
void cpufreq_dbs_timer_suspend(void);
|
||||
void cpufreq_dbs_timer_resume(void);
|
||||
|
||||
void cpufreq_dbs_enable_turbo(int cpuid);
|
||||
void cpufreq_dbs_disable_turbo(int cpuid);
|
||||
unsigned int cpufreq_dbs_get_turbo_status(int cpuid);
|
||||
#endif /* __XEN_CPUFREQ_PM_H__ */
|
||||
@@ -9,7 +9,6 @@
|
||||
int get_cpu_id(u8);
|
||||
int powernow_cpufreq_init(void);
|
||||
unsigned int powernow_register_driver(void);
|
||||
|
||||
void cpufreq_residency_update(unsigned int, uint8_t);
|
||||
void cpufreq_statistic_update(unsigned int, uint8_t, uint8_t);
|
||||
int cpufreq_statistic_init(unsigned int);
|
||||
|
||||
@@ -283,7 +283,6 @@ struct xen_ondemand {
|
||||
|
||||
uint32_t sampling_rate;
|
||||
uint32_t up_threshold;
|
||||
uint32_t turbo_enabled;
|
||||
};
|
||||
typedef struct xen_ondemand xen_ondemand_t;
|
||||
|
||||
@@ -319,6 +318,8 @@ struct xen_get_cpufreq_para {
|
||||
struct xen_userspace userspace;
|
||||
struct xen_ondemand ondemand;
|
||||
} u;
|
||||
|
||||
int32_t turbo_enabled;
|
||||
};
|
||||
|
||||
struct xen_set_cpufreq_gov {
|
||||
|
||||