The problem does also exist on Linux, but it’s a lot less noticeable. For a long-running or multi-thread, it’s only visible for the first few seconds. For burst single thread workload (e.g., rendering a web page on Firefox), however, it is perceivably slower.
I have a single thread unit test that does the latter on Linux, which finishes in 10 minutes on powersave
governor, and 3 minutes on performance
. Funnily enough, just having stress-ng --cpu 1
running in the background made it finish in 3 minutes.
On Linux, there are two more knobs that can affect this behavior:
- EPP located at
/sys/devices/system/cpu/cpu*/cpufreq/energy_performance_preference
(0-5 where 0 is performance and 5 is powersave)
- EPB located at
/sys/devices/system/cpu/cpu*/power/energy_perf_bias
(0-15 where 0 is performance and 15 is powersave)
By default, Linux will set energy_perf_bias
to 6
if it was set to 0
from the BIOS (i.e. the “Boot Performance”-esque setting on most BIOS). On SPR, I’ve found setting this value to 4
(balanced_performance
) or 0
(performance
) fixes the slowness issue for the aforementioned burst single-thread use case while not completely disabling C6 state.
I’m not aware of such a knob on Windows though I think you could write a program that manually writes to 0x1B0
MSR to control this behavior. It does appear that Windows is using a value lower than 6
for the Balanced Power Profile.
On a Supermicro board, there’s an explicit setting that allows disabling the OS ability to override EPB, so I can confirm the effect of EPB value on Windows. Setting this value on Supermicro board results in the following (on Windows with balanced profile):
CPU Configuration → Advanced Power Management Configuration
-
Power Technology: Custom
-
Power Performance Tuning: BIOS Controls EPB
-
ENERGY_PERF_BIAS_CFG: either
- Balanced Performance (idles ~50W, some lag, but not as annoying)
- Maximum Performance (idles ~70W, no lag)
When set this to Balanced Power, Windows idles at ~50W, but with severe lag. Anecdotally, Supermicro has switched the default settings to “BIOS Controls EPB” since BIOS 1.2 released last month.
My best guess of what EPB knob does is it makes the process enter C6 sleep state less, and/or keeps at least a single core out of that state. Setting EPB = 0 also makes the processor always boost at least a single core (while EPB = 4 doesn’t do that). It’s still different than High Performance profile, as Windows would still try to park the cores.
On Linux, I’ve resorted to this script, which does what I expect for what I would call a “balanced” profile (run: /path/to/script.sh balanced
):
#!/bin/sh
PROFILE=${1:-powersave}
EPB_DEFAULT=
EPP_DEFAULT=
case "$PROFILE" in
performance )
GOVERNOR=performance
EPB_DEFAULT=performance
EPP_DEFAULT=performance
;;
balanced )
GOVERNOR=powersave
EPB_DEFAULT=performance
EPP_DEFAULT=performance
;;
powersave )
GOVERNOR=powersave
EPB_DEFAULT=balance-power
EPP_DEFAULT=balance_power
;;
* )
echo >&1 "Unknown profile: $PROFILE"
exit 1
;;
esac
EPB=${2:-$EPB_DEFAULT}
EPP=${3:-$EPP_DEFAULT}
echo "Setting CPU Governor: $GOVERNOR"
cpupower frequency-set --governor "$GOVERNOR" >/dev/null
echo "Setting CPU Governor Energy Performance Preference: $EPP"
for n in /sys/devices/system/cpu/cpu*/cpufreq/energy_performance_preference; do
if ! [ -f "$n" ]; then
echo "Could not set Energy Performance Preference"
break
fi
echo "$EPP" > "$n"
done
echo "Setting CPU Energy Performance Bias: $EPB"
for n in /sys/devices/system/cpu/cpu*/power/energy_perf_bias; do
if ! [ -f "$n" ]; then
echo "Could not set Energy Performance Bias"
break
fi
echo "$EPB" > "$n"
done