问题
In Windows X86, the CPU brand can be queried with cpuid
intrinsic function.
Here is a sample of the code:
#include <stdio.h>
#include <intrin.h>
int main(void)
{
int cpubrand[4 * 3];
__cpuid(&cpubrand[0], 0x80000002);
__cpuid(&cpubrand[4], 0x80000003);
__cpuid(&cpubrand[8], 0x80000004);
char str[48];
memset(str, 0, sizeof str);
memcpy(str, cpubrand, sizeof cpubrand);
printf("%s\n", str);
}
What is the alternative of this in Windows ARM64?
回答1:
Not a way to get name directly from the CPU either, but you can get processor name from the WMI Win32_Processor class
It can be obtained by running wmic cpu get name
in cmd or (Get-WmiObject Win32_Processor).Name
in PowerShell. Getting it from C# is also easy, something like
ManagementObjectSearcher mos = new ManagementObjectSearcher("SELECT Name FROM Win32_Processor")
foreach (ManagementObject mo in mos.Get())
{
Console.WriteLine(mo["Name"]);
}
However doing that from C is a lot trickier. Luckily there's already a similar example in this answer. The main part should be like this
BSTR query = SysAllocString(L"SELECT Name FROM Win32_Processor");
hr = services->lpVtbl->ExecQuery(services, language, query, WBEM_FLAG_BIDIRECTIONAL, NULL, &results);
...
hr = result->lpVtbl->Get(result, L"Name", 0, &name, 0, 0);
SysFreeString(query);
回答2:
Although probably not the answer you're looking for (i.e. directly interrogating the CPU), you can fetch the "ProcessorNameString" value from the Windows Registry using code like the following:
#define BUFSIZ 64 // For easy adjustment of limits, if required
char answer[BUFSIZ] = "Error Reading CPU Name from Registry!", inBuffer[BUFSIZ] = "";
const char *csName = "HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0";
HKEY hKey; DWORD gotType, gotSize = BUFSIZ;
if (RegOpenKeyExA(HKEY_LOCAL_MACHINE, csName, 0, KEY_READ, &hKey) == ERROR_SUCCESS) {
if (!RegQueryValueExA(hKey, "ProcessorNameString", nullptr, &gotType, (PBYTE)(inBuffer), &gotSize)) {
if ((gotType == REG_SZ) && strlen(inBuffer)) strcpy(answer, inBuffer);
}
RegCloseKey(hKey);
}
This will (or should) give you the processor's 'name' that the Windows system sees! I don't have access to an ARM64
system, so I can't properly test it but, on my x64
system, I get the following (correct) string: Intel(R) Core(TM) i7-8550U CPU @ 1.80GHz
(which is exactly that returned by using __cpuid()
calls to get the "Brand String").
However, like you, I would be very interested to know of a way to do this directly - i.e., how would the Windows O/S get this info on an ARM64
system?
回答3:
The direct way to get this information would be to read the Main ID Register MIDR_EL1
. This could be done via the mrs
instruction in (inline) assembly or via the _ReadStatusReg
instrinct.
Unfortunately this register cannot be accessed from user mode (i.e. EL0
) and every attempt throws an exception. At Linux the behavior is then emulated so that MIDR_EL1
can still be accessed. However, I do not know or have the opportunity to test whether Windows also offers this feature.
References:
- ARM64 CPU Feature Registers at kernel.org (how Linux made
MIDR_EL1
accessible) - Main ID Register at developer.arm.com (from the Cortex-A53 docs)
- ARM64 Instrincts at Microsoft Docs
来源:https://stackoverflow.com/questions/60588765/how-to-get-cpu-brand-information-in-arm64