3

There are Windows API functions to obtain CPU and CPU Cache topology.

GetSystemInfo fills SYSTEM_INFO with dwActiveProcessorMask and dwNumberOfProcessors.

GetLogicalProcessorInformationEx can be used to have more precise information about each processor, like cache size, cache line size, cache associativity, etc. Some of this information can be obtained by _cpuidex as well.

I'm asking in which cases the obtained values for one call are not consistent with obtained values for another call, if both calls are made without program restart.

Specifically, can CPU count change:

  • Should user hibernate, install new processor, and wake the system? Or even this wouldn't work?
  • Or operating system / hardware can just dynamically decide to plug in another processor?
  • Or it can be achieved with virtual machines, but not on real hardware?

Can cache line size and cache size change:

  • For GetLogicalProcessorInformationEx, because processor is replaced at runtime
  • For _cpuid just because system contains processors with different cache properties, and subsequent calls are on a different processor

The practical reason for these questions is that I want to obtain this information only once, and cache it:

  • I'm going to use it for allocator tuning, so changing allocation strategy for already allocated memory is likely to cause memory corruption.
  • These function may be expensive, they may be kernel calls, which I want to avoid
magicandre1981
  • 27,895
  • 5
  • 86
  • 127
Alex Guteniev
  • 12,039
  • 2
  • 34
  • 79
  • It can certainly change in the hibernation case and on high-end server equipment it may be able to change even without that. And this can definitely occur on real hardware and not just VMs. Though you are unlikely to see it unless you are running on extremely specialized server grade equipment. – SoronelHaetir Jul 07 '20 at 04:56
  • I should say, I mean processor counts can change, I'm not sure whether cache lines are required to be the same for all CPUs, though I suppose if it were that would be part of GetSystemInformation and not GetLogicalProcessorInformationEx. – SoronelHaetir Jul 07 '20 at 04:58
  • Could you show more information about how to reproduce this issue? Like how to use `GetLogicalProcessorInformationEx` to get processors count? And your environment information like physical processors and logical processors count, your application target architecture (x86/x64/arm64) and your system architecture? – Rita Han Jul 07 '20 at 08:38
  • @Rita, I did not reproduce this behavior on a particular architecture. I want to know when this behavior is reproduced, in particular, on which architectures, if they differ in this regard. An example in `GetLogicalProcessorInformation` documentation contains CPU counting, the same can be done with Ex version – Alex Guteniev Jul 07 '20 at 08:48

1 Answers1

3

If a thread is scheduled to run on a core that belongs to a different processor group with a different number of processors, GetSystemInfo and GetLogicalProcessorInformation would return a different number of processors, which is the number of processors in the group that core belongs to.

On server-grade systems that support hot-adding CPUs, that number of processors can change as follows:

  • Hot-adding a CPU such that there is one processor group with less than 64 processors and the thread is running on that group would change the number of processors reported by GetSystemInfo, GetLogicalProcessorInformation, and GetLogicalProcessorInformationEx.
  • The maximum size of a processor group is 64 and Windows always creates groups in such way as to minimize the total number of groups. So the number of groups is the ceiling of the total number of logical cores divided by 64. Hot-adding a CPU may result in a creating a new group. This not only changes the total number of processors, but also the number of groups, which can only be obtained via GetLogicalProcessorInformationEx.

On a virtual machine, the number of processors can also increase dynamically without hot-plugging.

You can simulate hot-adding processors using the PNPCPU tool. This is useful for testing the correctness of a piece of a code that depends on the number of processors.

It's possible to receive a notification from the system when a new processor is added by writing a device driver and registering a synchronous or asynchronous driver notification. I don't think this is possible without a device driver.

I think, on current systems, cache properties returned by GetLogicalProcessorInformationEx can only change on thread migration to another core or CPU where one or more of these properties are different. For example, on an Intel Lakefield processor, the properties of the L2 cache depend which core the thread is running because different cores have different L2 caches of different properties.

Hadi Brais
  • 22,259
  • 3
  • 54
  • 95