Physical/Logical CPU Frequency Reporting with Hyper-V enabled
I always found it curious that with Hyper-V enabled, Task manager fails to report the actual CPU frequency and instead reports the nominal frequency. People much smarter than me have noticed this too but I haven't found a compelling explanation for why it doesn't work. I thought that maybe type-1 hypervisors prevent accurate reporting of CPU frequency and that maybe task manager was just detecting hyper-v and grabbing the frequency from a regkey like:
[HKEY_LOCAL_MACHINE\HARDWARE\DESCRIPTION\System\CentralProcessor\0] "~MHz"=dword:
But changing that regkey didn't change the reported frequency.
So what about 3rd-party tools? CPU-Z appears to report the CPU frequency correctly in real-time. What gives?
I was determined to find out what was going on and found some curious text on MSDN:
"Measure guest operating system processor utilization – Traditionally, processor performance can be measured using the “\Processor(*)\% Processor Time” performance monitor counter. This is not an accurate counter for evaluating processor utilization of a guest operating system though because Hyper-V measures and reports this value relative to the number of processors allocated to the virtual machine.
...
Hyper-V provides hypervisor performance objects to monitor the performance of both logical and virtual processors. A logical processor correlates directly to the number of processors or cores that are installed on the physical computer."
OK, so how do you just report the real-time CPU frequency of each CPU core with an easy to view graph just like task manager? Use the built-in Performance Monitor tool (perfmon.exe) and add the "\Hyper-V Hypervisor Logical Processor\Frequency" performance counter:
Add the counters for each CPU core:
Then right click on the y-axis and choose "properties" then "graph" to set the vertical scale to the max possible TurboBoost frequency. In this case my AMD A10-6700 quad-core APU goes to ~4300MHz:
I also added in the nominal processor frequency reported by the performance counter "Processor\Frequency" to get the solid line at 3700MHz as a reference point. And here is the graph showing the variable frequencies per core when loading and unloading the system with some D3D11 rendering:
Curiously, the reported frequency never goes above 3700MHz in perfmon, however, CPU-Z shows my processor peaking at around 4250MHz in turbo mode. Not sure how CPU-Z is getting those numbers. Maybe some custom assembly code for certain AMD and Intel processors? In any case, it seems like it would be simple to implement the hyper-V perf counters within Task Manager so at least you can see the frequency change in real-time. If folks would like to see this feature added to task manager, let me know and I'll reach out the appropriate team at Microsoft.
References:
- https://www.hanselman.com/blog/WindowsTaskManagerShowsWrongCPUSpeedWhenUsingHyperV.aspx
- https://msdn.microsoft.com/en-US/library/cc768535(v=bts.10).aspx
- https://www.dima.to/blog/?p=101
- https://superuser.com/questions/507717/processor-always-at-max-speed/508075#508075
- https://answers.microsoft.com/en-us/windows/forum/windows_8-performance/task-manager-shows-incorrect-cpu-frequency-after/acfb0567-1bf7-4b4a-ab96-ab9de3efaec2
Back to main blog: https://dancharblog.wordpress.com