Mercurial > illumos > illumos-gate
changeset 10992:54a1c1cbd683
6887944 support for IA32_ENERGY_PERF_BIAS MSR
author | aubrey.li@intel.com |
---|---|
date | Fri, 06 Nov 2009 19:10:07 -0800 |
parents | d59f9e6fc1f7 |
children | 3801a6f1e78e |
files | usr/src/uts/i86pc/os/cpuid.c usr/src/uts/i86pc/os/cpupm/cpupm_intel.c usr/src/uts/intel/sys/x86_archext.h |
diffstat | 3 files changed, 89 insertions(+), 0 deletions(-) [+] |
line wrap: on
line diff
--- a/usr/src/uts/i86pc/os/cpuid.c Sat Nov 07 02:08:39 2009 +0100 +++ b/usr/src/uts/i86pc/os/cpuid.c Fri Nov 06 19:10:07 2009 -0800 @@ -4145,6 +4145,33 @@ } } +/* + * Check support for Intel ENERGY_PERF_BIAS feature + */ +int +cpuid_iepb_supported(struct cpu *cp) +{ + struct cpuid_info *cpi = cp->cpu_m.mcpu_cpi; + struct cpuid_regs regs; + + ASSERT(cpuid_checkpass(cp, 1)); + + if (!(x86_feature & X86_CPUID) || !(x86_feature & X86_MSR)) { + return (0); + } + + /* + * Intel ENERGY_PERF_BIAS MSR is indicated by + * capability bit CPUID.6.ECX.3 + */ + if ((cpi->cpi_vendor != X86_VENDOR_Intel) || (cpi->cpi_maxeax < 6)) + return (0); + + regs.cp_eax = 0x6; + (void) cpuid_insn(NULL, ®s); + return (regs.cp_ecx & CPUID_EPB_SUPPORT); +} + #if defined(__amd64) && !defined(__xpv) /* * Patch in versions of bcopy for high performance Intel Nhm processors
--- a/usr/src/uts/i86pc/os/cpupm/cpupm_intel.c Sat Nov 07 02:08:39 2009 +0100 +++ b/usr/src/uts/i86pc/os/cpupm/cpupm_intel.c Fri Nov 06 19:10:07 2009 -0800 @@ -24,6 +24,11 @@ */ /* + * Copyright (c) 2009, Intel Corporation. + * All rights reserved. + */ + +/* * Intel specific CPU power management support. */ @@ -32,6 +37,7 @@ #include <sys/speedstep.h> #include <sys/cpupm_throttle.h> #include <sys/cpu_idle.h> +#include <sys/archsystm.h> /* * The Intel Processor Driver Capabilities (_PDC). @@ -51,6 +57,31 @@ static uint32_t cpupm_intel_pdccap = 0; +/* + * MSR for Intel ENERGY_PERF_BIAS feature. + * The default processor power operation policy is max performance. + * Power control unit drives to max performance at any energy cost. + * This MSR is designed to be a power master control knob, + * it provides 4-bit OS input to the HW for the logical CPU, based on + * user power-policy preference(scale of 0 to 15). 0 is highest + * performance, 15 is minimal energy consumption. + * 7 is a good balance between performance and energy consumption. + */ +#define IA32_ENERGY_PERF_BIAS_MSR 0x1B0 +#define EPB_MSR_MASK 0xF +#define EPB_MAX_PERF 0 +#define EPB_BALANCE 7 +#define EPB_MAX_POWER_SAVE 15 + +/* + * The value is used to initialize the user power policy preference + * in IA32_ENERGY_PERF_BIAS_MSR. Variable is used here to allow tuning + * from the /etc/system file. + */ +uint64_t cpupm_iepb_policy = EPB_MAX_PERF; + +static void cpupm_iepb_set_policy(uint64_t power_policy); + boolean_t cpupm_intel_init(cpu_t *cp) { @@ -105,5 +136,30 @@ (void) cpu_acpi_write_pdc(mach_state->ms_acpi_handle, CPUPM_INTEL_PDC_REVISION, 1, &cpupm_intel_pdccap); + /* + * If Intel ENERGY PERFORMANCE BIAS feature is supported, + * provides input to the HW, based on user power-policy. + */ + if (cpuid_iepb_supported(cp)) { + cpupm_iepb_set_policy(cpupm_iepb_policy); + } + return (B_TRUE); } + +/* + * ENERGY_PERF_BIAS setting, + * A hint to HW, based on user power-policy + */ +static void +cpupm_iepb_set_policy(uint64_t iepb_policy) +{ + ulong_t iflag; + uint64_t epb_value; + + epb_value = iepb_policy & EPB_MSR_MASK; + + iflag = intr_clear(); + wrmsr(IA32_ENERGY_PERF_BIAS_MSR, epb_value); + intr_restore(iflag); +}
--- a/usr/src/uts/intel/sys/x86_archext.h Sat Nov 07 02:08:39 2009 +0100 +++ b/usr/src/uts/intel/sys/x86_archext.h Fri Nov 06 19:10:07 2009 -0800 @@ -383,6 +383,11 @@ #define CPUID_CSTATE_ARAT (0x4) /* + * Intel ENERGY_PERF_BIAS MSR indicated by feature bit CPUID.6.ECX[3]. + */ +#define CPUID_EPB_SUPPORT (1 << 3) + +/* * x86_type is a legacy concept; this is supplanted * for most purposes by x86_feature; modern CPUs * should be X86_TYPE_OTHER @@ -657,6 +662,7 @@ extern void cpuid_mwait_free(struct cpu *); extern int cpuid_deep_cstates_supported(void); extern int cpuid_arat_supported(void); +extern int cpuid_iepb_supported(struct cpu *); extern int vmware_platform(void); #endif