https://git.reactos.org/?p=reactos.git;a=commitdiff;h=fa52f2fae0b73ca10e18fe...
commit fa52f2fae0b73ca10e18fe187b0dff16cfaabfc8 Author: Marcus Boillat marcus.boillat@gmail.com AuthorDate: Sun May 8 19:27:27 2022 +0200 Commit: Stanislav Motylkov x86corez@gmail.com CommitDate: Mon May 9 21:50:24 2022 +0300
[NTOS:KE] Fix CPU extended family and model detection
Based on documentation from Geoff Chappell: https://www.geoffchappell.com/studies/windows/km/cpu/cpuid/00000001h/eax.htm
CORE-17974 --- ntoskrnl/ke/amd64/cpu.c | 29 +++++++++++++++++++++++++++-- ntoskrnl/ke/i386/cpu.c | 23 +++++++++++++++++++++++ 2 files changed, 50 insertions(+), 2 deletions(-)
diff --git a/ntoskrnl/ke/amd64/cpu.c b/ntoskrnl/ke/amd64/cpu.c index 4ed7e5470fe..d4a8888c664 100644 --- a/ntoskrnl/ke/amd64/cpu.c +++ b/ntoskrnl/ke/amd64/cpu.c @@ -98,7 +98,11 @@ KiSetProcessorType(VOID) { CPU_INFO CpuInfo; CPU_SIGNATURE CpuSignature; - ULONG Stepping, Type; + BOOLEAN ExtendModel; + ULONG Stepping, Type, Vendor; + + /* This initializes Prcb->CpuVendor */ + Vendor = KiGetCpuVendor();
/* Do CPUID 1 now */ KiCpuId(&CpuInfo, 1); @@ -111,8 +115,29 @@ KiSetProcessorType(VOID) */ CpuSignature.AsULONG = CpuInfo.Eax; Stepping = CpuSignature.Model; + ExtendModel = (CpuSignature.Family == 15); +#if ( (NTDDI_VERSION >= NTDDI_WINXPSP2) && (NTDDI_VERSION < NTDDI_WS03) ) || (NTDDI_VERSION >= NTDDI_WS03SP1) + if (CpuSignature.Family == 6) + { + ExtendModel |= (Vendor == CPU_INTEL); +#if (NTDDI_VERSION >= NTDDI_WIN8) + ExtendModel |= (Vendor == CPU_CENTAUR); +#endif + } +#endif + if (ExtendModel) + { + /* Add ExtendedModel to distinguish from non-extended values. */ + Stepping |= (CpuSignature.ExtendedModel << 4); + } Stepping = (Stepping << 8) | CpuSignature.Step; Type = CpuSignature.Family; + if (CpuSignature.Family == 15) + { + /* Add ExtendedFamily to distinguish from non-extended values. + * It must not be larger than 0xF0 to avoid overflow. */ + Type += min(CpuSignature.ExtendedFamily, 0xF0); + }
/* Save them in the PRCB */ KeGetCurrentPrcb()->CpuID = TRUE; @@ -130,7 +155,7 @@ KiGetFeatureBits(VOID) CPU_INFO CpuInfo;
/* Get the Vendor ID */ - Vendor = KiGetCpuVendor(); + Vendor = Prcb->CpuVendor;
/* Make sure we got a valid vendor ID at least. */ if (!Vendor) return FeatureBits; diff --git a/ntoskrnl/ke/i386/cpu.c b/ntoskrnl/ke/i386/cpu.c index 711070eeb07..0e4b8fa8468 100644 --- a/ntoskrnl/ke/i386/cpu.c +++ b/ntoskrnl/ke/i386/cpu.c @@ -159,6 +159,7 @@ KiSetProcessorType(VOID) { CPU_INFO CpuInfo; CPU_SIGNATURE CpuSignature; + BOOLEAN ExtendModel; ULONG Stepping, Type;
/* Do CPUID 1 now */ @@ -172,8 +173,30 @@ KiSetProcessorType(VOID) */ CpuSignature.AsULONG = CpuInfo.Eax; Stepping = CpuSignature.Model; + ExtendModel = (CpuSignature.Family == 15); +#if ( (NTDDI_VERSION >= NTDDI_WINXPSP2) && (NTDDI_VERSION < NTDDI_WS03) ) || (NTDDI_VERSION >= NTDDI_WS03SP1) + if (CpuSignature.Family == 6) + { + ULONG Vendor = KiGetCpuVendor(); + ExtendModel |= (Vendor == CPU_INTEL); +#if (NTDDI_VERSION >= NTDDI_WIN8) + ExtendModel |= (Vendor == CPU_CENTAUR); +#endif + } +#endif + if (ExtendModel) + { + /* Add ExtendedModel to distinguish from non-extended values. */ + Stepping |= (CpuSignature.ExtendedModel << 4); + } Stepping = (Stepping << 8) | CpuSignature.Step; Type = CpuSignature.Family; + if (CpuSignature.Family == 15) + { + /* Add ExtendedFamily to distinguish from non-extended values. + * It must not be larger than 0xF0 to avoid overflow. */ + Type += min(CpuSignature.ExtendedFamily, 0xF0); + }
/* Save them in the PRCB */ KeGetCurrentPrcb()->CpuID = TRUE;