ia64/xen-unstable

changeset 18917:b56d5fe594ae

x86, cpufreq: Change cpufreq_driver->get so that it can get other
cpu's real physical freq.

Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>
author Keir Fraser <keir.fraser@citrix.com>
date Thu Dec 11 11:49:37 2008 +0000 (2008-12-11)
parents 2941b1a97c60
children 33ae75b60de2
files xen/arch/x86/acpi/cpufreq/cpufreq.c
line diff
     1.1 --- a/xen/arch/x86/acpi/cpufreq/cpufreq.c	Thu Dec 11 11:48:19 2008 +0000
     1.2 +++ b/xen/arch/x86/acpi/cpufreq/cpufreq.c	Thu Dec 11 11:49:37 2008 +0000
     1.3 @@ -131,10 +131,13 @@ struct drv_cmd {
     1.4      u32 val;
     1.5  };
     1.6  
     1.7 -static void do_drv_read(struct drv_cmd *cmd)
     1.8 +static void do_drv_read(void *drvcmd)
     1.9  {
    1.10 +    struct drv_cmd *cmd;
    1.11      u32 h;
    1.12  
    1.13 +    cmd = (struct drv_cmd *)drvcmd;
    1.14 +
    1.15      switch (cmd->type) {
    1.16      case SYSTEM_INTEL_MSR_CAPABLE:
    1.17          rdmsr(cmd->addr.msr.reg, cmd->val, h);
    1.18 @@ -174,7 +177,13 @@ static void drv_read(struct drv_cmd *cmd
    1.19  {
    1.20      cmd->val = 0;
    1.21  
    1.22 -    do_drv_read(cmd);
    1.23 +    ASSERT(cpus_weight(cmd->mask) == 1);
    1.24 +
    1.25 +    /* to reduce IPI for the sake of performance */
    1.26 +    if (cpu_isset(smp_processor_id(), cmd->mask))
    1.27 +        do_drv_read((void *)cmd);
    1.28 +    else
    1.29 +        on_selected_cpus( cmd->mask, do_drv_read, (void *)cmd, 0, 1);
    1.30  }
    1.31  
    1.32  static void drv_write(struct drv_cmd *cmd)
    1.33 @@ -184,13 +193,21 @@ static void drv_write(struct drv_cmd *cm
    1.34  
    1.35  static u32 get_cur_val(cpumask_t mask)
    1.36  {
    1.37 +    struct cpufreq_policy *policy;
    1.38      struct processor_performance *perf;
    1.39      struct drv_cmd cmd;
    1.40 +    unsigned int cpu;
    1.41  
    1.42      if (unlikely(cpus_empty(mask)))
    1.43          return 0;
    1.44  
    1.45 -    switch (drv_data[first_cpu(mask)]->cpu_feature) {
    1.46 +    cpu = first_cpu(mask);
    1.47 +    policy = cpufreq_cpu_policy[cpu];
    1.48 +
    1.49 +    if (!policy)
    1.50 +        return 0;    
    1.51 +
    1.52 +    switch (drv_data[policy->cpu]->cpu_feature) {
    1.53      case SYSTEM_INTEL_MSR_CAPABLE:
    1.54          cmd.type = SYSTEM_INTEL_MSR_CAPABLE;
    1.55          cmd.addr.msr.reg = MSR_IA32_PERF_STATUS;
    1.56 @@ -205,7 +222,7 @@ static u32 get_cur_val(cpumask_t mask)
    1.57          return 0;
    1.58      }
    1.59  
    1.60 -    cmd.mask = mask;
    1.61 +    cmd.mask = cpumask_of_cpu(cpu);
    1.62  
    1.63      drv_read(&cmd);
    1.64      return cmd.val;
    1.65 @@ -280,13 +297,18 @@ static unsigned int get_measured_perf(un
    1.66  
    1.67  static unsigned int get_cur_freq_on_cpu(unsigned int cpu)
    1.68  {
    1.69 -    struct acpi_cpufreq_data *data = drv_data[cpu];
    1.70 +    struct cpufreq_policy *policy;
    1.71 +    struct acpi_cpufreq_data *data;
    1.72      unsigned int freq;
    1.73  
    1.74 +    policy = cpufreq_cpu_policy[cpu];
    1.75 +    if (!policy)
    1.76 +        return 0;
    1.77 +
    1.78 +    data = drv_data[policy->cpu];
    1.79      if (unlikely(data == NULL ||
    1.80 -        data->acpi_data == NULL || data->freq_table == NULL)) {
    1.81 +        data->acpi_data == NULL || data->freq_table == NULL))
    1.82          return 0;
    1.83 -    }
    1.84  
    1.85      freq = extract_freq(get_cur_val(cpumask_of_cpu(cpu)), data);
    1.86      return freq;