Signed-off-by: Alex Henrie alexhenrie24@gmail.com --- dlls/kernel32/process.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/dlls/kernel32/process.c b/dlls/kernel32/process.c index b8a0c823398..c1c3c484493 100644 --- a/dlls/kernel32/process.c +++ b/dlls/kernel32/process.c @@ -611,7 +611,7 @@ DWORD WINAPI GetActiveProcessorCount(WORD group) { DWORD cpus = system_info.NumberOfProcessors;
- FIXME("semi-stub, returning %u\n", cpus); + FIXME("(0x%x): semi-stub, returning %u\n", group, cpus); return cpus; }
@@ -622,7 +622,7 @@ DWORD WINAPI GetMaximumProcessorCount(WORD group) { DWORD cpus = system_info.NumberOfProcessors;
- FIXME("semi-stub, returning %u\n", cpus); + FIXME("(0x%x): semi-stub, returning %u\n", group, cpus); return cpus; }
Signed-off-by: Alex Henrie alexhenrie24@gmail.com --- dlls/kernel32/tests/process.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+)
diff --git a/dlls/kernel32/tests/process.c b/dlls/kernel32/tests/process.c index 7c6a0ff0a84..ea9cde5facc 100644 --- a/dlls/kernel32/tests/process.c +++ b/dlls/kernel32/tests/process.c @@ -90,6 +90,8 @@ static SIZE_T (WINAPI *pGetLargePageMinimum)(void); static BOOL (WINAPI *pInitializeProcThreadAttributeList)(struct _PROC_THREAD_ATTRIBUTE_LIST*, DWORD, DWORD, SIZE_T*); static BOOL (WINAPI *pUpdateProcThreadAttribute)(struct _PROC_THREAD_ATTRIBUTE_LIST*, DWORD, DWORD_PTR, void *,SIZE_T,void*,SIZE_T*); static void (WINAPI *pDeleteProcThreadAttributeList)(struct _PROC_THREAD_ATTRIBUTE_LIST*); +static DWORD (WINAPI *pGetActiveProcessorCount)(WORD); +static DWORD (WINAPI *pGetMaximumProcessorCount)(WORD);
/* ############################### */ static char base[MAX_PATH]; @@ -270,6 +272,8 @@ static BOOL init(void) pInitializeProcThreadAttributeList = (void *)GetProcAddress(hkernel32, "InitializeProcThreadAttributeList"); pUpdateProcThreadAttribute = (void *)GetProcAddress(hkernel32, "UpdateProcThreadAttribute"); pDeleteProcThreadAttributeList = (void *)GetProcAddress(hkernel32, "DeleteProcThreadAttributeList"); + pGetActiveProcessorCount = (void *)GetProcAddress(hkernel32, "GetActiveProcessorCount"); + pGetMaximumProcessorCount = (void *)GetProcAddress(hkernel32, "GetMaximumProcessorCount");
return TRUE; } @@ -2320,6 +2324,23 @@ static void test_SystemInfo(void) } }
+static void test_ProcessorCount(void) +{ + DWORD active, maximum; + + if (!pGetActiveProcessorCount || !pGetMaximumProcessorCount) + { + win_skip("GetActiveProcessorCount or GetMaximumProcessorCount is not available\n"); + return; + } + + active = pGetActiveProcessorCount(ALL_PROCESSOR_GROUPS); + maximum = pGetMaximumProcessorCount(ALL_PROCESSOR_GROUPS); + ok(active <= maximum, + "Number of active processors %i is greater than maximum number of processors %i\n", + active, maximum); +} + static void test_RegistryQuota(void) { BOOL ret; @@ -4257,6 +4278,7 @@ START_TEST(process) test_IsWow64Process(); test_IsWow64Process2(); test_SystemInfo(); + test_ProcessorCount(); test_RegistryQuota(); test_DuplicateHandle(); test_StartupNoConsole();
Hi,
While running your changed tests, I think I found new failures. Being a bot and all I'm not very good at pattern recognition, so I might be wrong, but could you please double-check?
Full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=83346
Your paranoid android.
=== w1064 (32 bit report) ===
kernel32: process.c:4043: Test failed: Got unexpected ret 0x1, GetLastError() 1813. process.c:4057: Test failed: Got unexpected ret 0x1, GetLastError() 1813. process.c:3986: Test failed: Got unexpected ret 0, level 2, GetLastError() 6. process.c:3993: Test failed: Got parent id 296, parent_data.parent_id 0. process.c:4137: Test failed: Unexpected return value, error 203.
=== w10pro64_ar (64 bit report) ===
kernel32: process.c:4137: Test failed: Unexpected return value, error 203.
Signed-off-by: Alex Henrie alexhenrie24@gmail.com --- https://www.geoffchappell.com/studies/windows/km/ntoskrnl/api/ex/sysinfo/pro... --- dlls/ntdll/unix/system.c | 29 +++++++++++++++++++++++++++++ include/winternl.h | 2 +- 2 files changed, 30 insertions(+), 1 deletion(-)
diff --git a/dlls/ntdll/unix/system.c b/dlls/ntdll/unix/system.c index a889b2e020c..d34a3229816 100644 --- a/dlls/ntdll/unix/system.c +++ b/dlls/ntdll/unix/system.c @@ -170,6 +170,31 @@ struct smbios_boot_info
static SYSTEM_CPU_INFORMATION cpu_info;
+static int get_possible_cpus(void) +{ + int ret = NtCurrentTeb()->Peb->NumberOfProcessors; +#ifdef linux + FILE *f = fopen("/sys/devices/system/cpu/possible", "r"); + char line[32]; + char *value; + if (f) + { + if (fgets(line, sizeof(line), f)) + { + value = strchr(line, '-'); + if (value) + { + *value = 0; + value++; + ret = atoi(value) - atoi(line) + 1; + } + } + fclose(f); + } +#endif + return ret; +} + /******************************************************************************* * Architecture specific feature detection for CPUs * @@ -267,6 +292,8 @@ static void get_cpuinfo( SYSTEM_CPU_INFORMATION *info ) info->Architecture = PROCESSOR_ARCHITECTURE_AMD64; #endif
+ info->MaximumCpus = get_possible_cpus(); + /* We're at least a 386 */ info->FeatureSet = CPU_FEATURE_VME | CPU_FEATURE_X86 | CPU_FEATURE_PGE; info->Level = 3; @@ -415,6 +442,7 @@ static inline void get_cpuinfo( SYSTEM_CPU_INFORMATION *info ) FIXME("CPU Feature detection not implemented.\n"); #endif info->Architecture = PROCESSOR_ARCHITECTURE_ARM; + info->MaximumCpus = get_possible_cpus(); }
#elif defined(__aarch64__) @@ -463,6 +491,7 @@ static void get_cpuinfo( SYSTEM_CPU_INFORMATION *info ) #endif info->Level = max(info->Level, 8); info->Architecture = PROCESSOR_ARCHITECTURE_ARM64; + info->MaximumCpus = get_possible_cpus(); }
#endif /* End architecture specific feature detection for CPUs */ diff --git a/include/winternl.h b/include/winternl.h index a7b0e04aade..4d207f9cd17 100644 --- a/include/winternl.h +++ b/include/winternl.h @@ -1691,7 +1691,7 @@ typedef struct _SYSTEM_CPU_INFORMATION { WORD Architecture; WORD Level; WORD Revision; /* combination of CPU model and stepping */ - WORD Reserved; /* always zero */ + WORD MaximumCpus; /* number of CPUs if as many as possible are hot-added */ DWORD FeatureSet; /* see bit flags below */ } SYSTEM_CPU_INFORMATION, *PSYSTEM_CPU_INFORMATION;
Signed-off-by: Alex Henrie alexhenrie24@gmail.com --- This fixes the console spam when the Clinithink natural language processing software https://www.clinithink.com/ calls GetMaximumProcessorCount repeatedly. --- dlls/kernel32/kernel_main.c | 1 + dlls/kernel32/kernel_private.h | 1 + dlls/kernel32/process.c | 9 +++++++-- 3 files changed, 9 insertions(+), 2 deletions(-)
diff --git a/dlls/kernel32/kernel_main.c b/dlls/kernel32/kernel_main.c index 89394e16430..531a580749f 100644 --- a/dlls/kernel32/kernel_main.c +++ b/dlls/kernel32/kernel_main.c @@ -123,6 +123,7 @@ static BOOL process_attach( HMODULE module ) RtlSetUnhandledExceptionFilter( UnhandledExceptionFilter );
NtQuerySystemInformation( SystemBasicInformation, &system_info, sizeof(system_info), NULL ); + NtQuerySystemInformation( SystemCpuInformation, &cpu_info, sizeof(cpu_info), NULL );
copy_startup_info();
diff --git a/dlls/kernel32/kernel_private.h b/dlls/kernel32/kernel_private.h index 633511d6140..cbd23f52f10 100644 --- a/dlls/kernel32/kernel_private.h +++ b/dlls/kernel32/kernel_private.h @@ -30,6 +30,7 @@ static inline BOOL set_ntstatus( NTSTATUS status ) }
extern SYSTEM_BASIC_INFORMATION system_info DECLSPEC_HIDDEN; +extern SYSTEM_CPU_INFORMATION cpu_info DECLSPEC_HIDDEN;
extern WCHAR *FILE_name_AtoW( LPCSTR name, BOOL alloc ) DECLSPEC_HIDDEN; extern DWORD FILE_name_WtoA( LPCWSTR src, INT srclen, LPSTR dest, INT destlen ) DECLSPEC_HIDDEN; diff --git a/dlls/kernel32/process.c b/dlls/kernel32/process.c index c1c3c484493..564fa703b5a 100644 --- a/dlls/kernel32/process.c +++ b/dlls/kernel32/process.c @@ -50,6 +50,7 @@ typedef struct } LOADPARMS32;
SYSTEM_BASIC_INFORMATION system_info = { 0 }; +SYSTEM_CPU_INFORMATION cpu_info = { 0 };
/* Process flags */ #define PDB32_DEBUGGED 0x0001 /* Process is being debugged */ @@ -620,9 +621,13 @@ DWORD WINAPI GetActiveProcessorCount(WORD group) */ DWORD WINAPI GetMaximumProcessorCount(WORD group) { - DWORD cpus = system_info.NumberOfProcessors; + DWORD cpus = cpu_info.MaximumCpus; + + if (group == ALL_PROCESSOR_GROUPS) + TRACE("(0x%x): returning %u\n", group, cpus); + else + FIXME("(0x%x): processor groups not supported, returning %u\n", group, cpus);
- FIXME("(0x%x): semi-stub, returning %u\n", group, cpus); return cpus; }