Support multiple processor groups for NativeAOT #75165
Merged
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
At present, NativeAOT does not account for availability of multiple processor groups on Windows 11+. For instance,
Environment.ProcessorCountreturns either64or16on an 80 core Ampere machine. Furthermore, settingDOTNET_GCCpuGroup=1has no effect, because we access that setting (RhInitialize⭢PalInit⭢GCToOSInterface::Initialize⭢InitCPUGroupInfo⭢GCConfig::GetGCCpuGroup) before it is initialized (RhInitialize⭢InitDLL⭢RedhawkGCInterface::InitializeSubsystems⭢GCHeapUtilities::InitializeDefaultGC⭢GC_Initialize⭢GCConfig::Initialize).This PR changes the NativeAOT runtime to use the same logic regarding multiple processor groups as in CoreCLR. Namely, it allows the
DOTNET_GCCpuGroupconfiguration setting to control whether the runtime may use all processor groups. If the setting is not provided, it defaults totruefor a non-affinitized process on Windows 11+ with multiple processor groups and tofalseotherwise (see related #68639 for CoreCLR).To fix the issue with accessing
GCConfigbefore it is initialized, we now callGCConfig::Initializebefore doingGCToOSInterface::Initialize. That makes the behavior of NativeAOT consistent with that of CoreCLR and the standalone GC case.However, that means that
GCConfig::Initializecan no longer check thePalGetProcessCpuCount() > 1condition to choose theServerGCconfiguration value (since the CPU count depends onGCToOSInterface::Initialize, which has not been called yet). Arguably, that wasn't good design, and this PR avoids this circular dependency by keeping theServerGCconfiguration value intact and choosing betweenSVRandWKSmodes when we actually initialize the GC.This PR also removes the unused
g_fHadSingleProcessorAtStartupflag and enables theGetGroupForProcessorfunction for NativeAOT.