From f27b62206cf3ee11e933d46a62ed56828070eb3f Mon Sep 17 00:00:00 2001 From: Nikolay Sivov Date: Wed, 6 Dec 2023 17:38:40 +0100 Subject: [PATCH] kernel32: Implement GetProcessInformation(ProcessMachineTypeInfo). Signed-off-by: Nikolay Sivov --- dlls/kernel32/kernel32.spec | 1 + dlls/kernel32/tests/process.c | 57 +++++++++++++++++++++++++++++++++ dlls/kernelbase/kernelbase.spec | 2 +- dlls/kernelbase/process.c | 51 +++++++++++++++++++++++++++++ dlls/win32u/freetype.c | 2 ++ dlls/winemac.drv/macdrv_cocoa.h | 2 ++ dlls/winspool.drv/cups.c | 2 ++ include/winbase.h | 15 +++++++++ 8 files changed, 131 insertions(+), 1 deletion(-) diff --git a/dlls/kernel32/kernel32.spec b/dlls/kernel32/kernel32.spec index 4815689a258..bb9c8fbfe0e 100644 --- a/dlls/kernel32/kernel32.spec +++ b/dlls/kernel32/kernel32.spec @@ -798,6 +798,7 @@ @ stdcall -import GetProcessHeaps(long ptr) RtlGetProcessHeaps @ stdcall -import GetProcessId(long) @ stdcall -import GetProcessIdOfThread(long) +@ stdcall GetProcessInformation(long long ptr long) @ stdcall GetProcessIoCounters(long ptr) @ stdcall -import GetProcessMitigationPolicy(long long ptr long) @ stdcall -import GetProcessPreferredUILanguages(long ptr ptr ptr) diff --git a/dlls/kernel32/tests/process.c b/dlls/kernel32/tests/process.c index d59074b988c..5f5327245fc 100644 --- a/dlls/kernel32/tests/process.c +++ b/dlls/kernel32/tests/process.c @@ -96,6 +96,7 @@ static BOOL (WINAPI *pUpdateProcThreadAttribute)(struct _PROC_THREAD_ATTRIBUTE static void (WINAPI *pDeleteProcThreadAttributeList)(struct _PROC_THREAD_ATTRIBUTE_LIST*); static DWORD (WINAPI *pGetActiveProcessorCount)(WORD); static DWORD (WINAPI *pGetMaximumProcessorCount)(WORD); +static BOOL (WINAPI *pGetProcessInformation)(HANDLE,PROCESS_INFORMATION_CLASS,void*,DWORD); /* ############################### */ static char base[MAX_PATH]; @@ -282,6 +283,7 @@ static BOOL init(void) pDeleteProcThreadAttributeList = (void *)GetProcAddress(hkernel32, "DeleteProcThreadAttributeList"); pGetActiveProcessorCount = (void *)GetProcAddress(hkernel32, "GetActiveProcessorCount"); pGetMaximumProcessorCount = (void *)GetProcAddress(hkernel32, "GetMaximumProcessorCount"); + pGetProcessInformation = (void *)GetProcAddress(hkernel32, "GetProcessInformation"); return TRUE; } @@ -5279,6 +5281,60 @@ static void test_startupinfo( void ) params->dwFlags ^= STARTF_USESTDHANDLES; } +static void test_GetProcessInformation(void) +{ + SYSTEM_SUPPORTED_PROCESSOR_ARCHITECTURES_INFORMATION machines[8]; + PROCESS_MACHINE_INFORMATION mi; + NTSTATUS status; + HANDLE process; + unsigned int i; + BOOL ret; + + if (!pGetProcessInformation) + { + win_skip("GetProcessInformation() is not available.\n"); + return; + } + + ret = pGetProcessInformation(GetCurrentProcess(), ProcessMachineTypeInfo, NULL, 0); + ok(!ret, "Unexpected return value %d.\n", ret); + ok(GetLastError() == ERROR_BAD_LENGTH, "Unexpected error %ld.\n", GetLastError()); + ret = pGetProcessInformation(GetCurrentProcess(), ProcessMachineTypeInfo, &mi, 0); + ok(!ret, "Unexpected return value %d.\n", ret); + ok(GetLastError() == ERROR_BAD_LENGTH, "Unexpected error %ld.\n", GetLastError()); + ret = pGetProcessInformation(GetCurrentProcess(), ProcessMachineTypeInfo, &mi, sizeof(mi) - 1); + ok(!ret, "Unexpected return value %d.\n", ret); + ok(GetLastError() == ERROR_BAD_LENGTH, "Unexpected error %ld.\n", GetLastError()); + ret = pGetProcessInformation(GetCurrentProcess(), ProcessMachineTypeInfo, &mi, sizeof(mi) + 1); + ok(!ret, "Unexpected return value %d.\n", ret); + ok(GetLastError() == ERROR_BAD_LENGTH, "Unexpected error %ld.\n", GetLastError()); + + ret = pGetProcessInformation(GetCurrentProcess(), ProcessMachineTypeInfo, &mi, sizeof(mi)); + ok(ret, "Unexpected return value %d.\n", ret); + + process = GetCurrentProcess(); + status = NtQuerySystemInformationEx( SystemSupportedProcessorArchitectures, &process, sizeof(process), + machines, sizeof(machines), NULL ); + ok(!status, "Failed to get architectures information.\n"); + for (i = 0; machines[i].Machine; i++) + { + if (machines[i].Process) + { + ok(mi.ProcessMachine == machines[i].Machine, "Unexpected process machine %#x.\n", mi.ProcessMachine); + ok(!mi.Res0, "Unexpected process machine %#x.\n", mi.ProcessMachine); + ok(!!(mi.MachineAttributes & UserEnabled) == machines[i].UserMode, "Unexpected attributes %#x.\n", + mi.MachineAttributes); + ok(!!(mi.MachineAttributes & KernelEnabled) == machines[i].KernelMode, "Unexpected attributes %#x.\n", + mi.MachineAttributes); + ok(!!(mi.MachineAttributes & Wow64Container) == machines[i].WoW64Container, "Unexpected attributes %#x.\n", + mi.MachineAttributes); + ok(!(mi.MachineAttributes & ~(UserEnabled | KernelEnabled | Wow64Container)), "Unexpected attributes %#x.\n", + mi.MachineAttributes); + break; + } + } +} + START_TEST(process) { HANDLE job, hproc, h, h2; @@ -5408,6 +5464,7 @@ START_TEST(process) test_dead_process(); test_services_exe(); test_startupinfo(); + test_GetProcessInformation(); /* things that can be tested: * lookup: check the way program to be executed is searched diff --git a/dlls/kernelbase/kernelbase.spec b/dlls/kernelbase/kernelbase.spec index e85f2b67d74..ffb153a46ee 100644 --- a/dlls/kernelbase/kernelbase.spec +++ b/dlls/kernelbase/kernelbase.spec @@ -660,7 +660,7 @@ @ stdcall GetProcessIdOfThread(long) @ stdcall GetProcessImageFileNameA(long ptr long) @ stdcall GetProcessImageFileNameW(long ptr long) -# @ stub GetProcessInformation +@ stdcall GetProcessInformation(long long ptr long) @ stdcall GetProcessMemoryInfo(long ptr long) @ stdcall GetProcessMitigationPolicy(long long ptr long) @ stdcall GetProcessPreferredUILanguages(long ptr ptr ptr) diff --git a/dlls/kernelbase/process.c b/dlls/kernelbase/process.c index 0c5104e7452..1aeb8f55257 100644 --- a/dlls/kernelbase/process.c +++ b/dlls/kernelbase/process.c @@ -1038,6 +1038,57 @@ BOOL WINAPI DECLSPEC_HOTPATCH IsWow64Process( HANDLE process, PBOOL wow64 ) return set_ntstatus( status ); } +/********************************************************************* + * GetProcessInformation (kernelbase.@) + */ +BOOL WINAPI GetProcessInformation( HANDLE process, PROCESS_INFORMATION_CLASS info_class, void *data, DWORD size ) +{ + switch (info_class) + { + case ProcessMachineTypeInfo: + { + PROCESS_MACHINE_INFORMATION *mi = data; + SYSTEM_SUPPORTED_PROCESSOR_ARCHITECTURES_INFORMATION machines[8]; + NTSTATUS status; + ULONG i; + + if (size != sizeof(*mi)) + { + SetLastError(ERROR_BAD_LENGTH); + return FALSE; + } + + status = NtQuerySystemInformationEx( SystemSupportedProcessorArchitectures, &process, sizeof(process), + machines, sizeof(machines), NULL ); + if (status) return set_ntstatus( status ); + + for (i = 0; machines[i].Machine; i++) + { + if (machines[i].Process) + { + mi->ProcessMachine = machines[i].Machine; + mi->Res0 = 0; + mi->MachineAttributes = 0; + if (machines[i].KernelMode) + mi->MachineAttributes |= KernelEnabled; + if (machines[i].UserMode) + mi->MachineAttributes |= UserEnabled; + if (machines[i].WoW64Container) + mi->MachineAttributes |= Wow64Container; + + return TRUE; + } + } + + break; + } + default: + FIXME("Unsupported information class %d.\n", info_class); + } + + return FALSE; +} + /********************************************************************* * OpenProcess (kernelbase.@) diff --git a/dlls/win32u/freetype.c b/dlls/win32u/freetype.c index 6043c66bc53..701e15c110d 100644 --- a/dlls/win32u/freetype.c +++ b/dlls/win32u/freetype.c @@ -46,6 +46,7 @@ #define CompareString __carbon_CompareString #define GetCurrentThread __carbon_GetCurrentThread #define GetCurrentProcess __carbon_GetCurrentProcess +#define GetProcessInformation __carbon_GetProcessInformation #define AnimatePalette __carbon_AnimatePalette #define DeleteMenu __carbon_DeleteMenu #define DrawMenu __carbon_DrawMenu @@ -72,6 +73,7 @@ #undef GetCurrentThread #undef _CDECL #undef GetCurrentProcess +#undef GetProcessInformation #undef AnimatePalette #undef CheckMenuItem #undef DeleteMenu diff --git a/dlls/winemac.drv/macdrv_cocoa.h b/dlls/winemac.drv/macdrv_cocoa.h index 6eff82ca122..3a977f68955 100644 --- a/dlls/winemac.drv/macdrv_cocoa.h +++ b/dlls/winemac.drv/macdrv_cocoa.h @@ -30,6 +30,7 @@ #define GetCurrentProcess MacGetCurrentProcess #define GetCurrentThread MacGetCurrentThread +#define GetProcessInformation MacGetProcessInformation #define LoadResource MacLoadResource #define AnimatePalette MacAnimatePalette #define EqualRgn MacEqualRgn @@ -59,6 +60,7 @@ #undef GetCurrentProcess #undef GetCurrentThread +#undef GetProcessInformation #undef LoadResource #undef AnimatePalette #undef EqualRgn diff --git a/dlls/winspool.drv/cups.c b/dlls/winspool.drv/cups.c index 6ad270709cc..8cdc193d33a 100644 --- a/dlls/winspool.drv/cups.c +++ b/dlls/winspool.drv/cups.c @@ -44,6 +44,7 @@ #ifdef __APPLE__ #define GetCurrentProcess GetCurrentProcess_Mac #define GetCurrentThread GetCurrentThread_Mac +#define GetProcessInformation GetProcessInformation_Mac #define LoadResource LoadResource_Mac #define AnimatePalette AnimatePalette_Mac #define EqualRgn EqualRgn_Mac @@ -71,6 +72,7 @@ #include #undef GetCurrentProcess #undef GetCurrentThread +#undef GetProcessInformation #undef LoadResource #undef AnimatePalette #undef EqualRgn diff --git a/include/winbase.h b/include/winbase.h index 16e449f7c2d..fe143cc7a61 100644 --- a/include/winbase.h +++ b/include/winbase.h @@ -1771,6 +1771,20 @@ typedef struct _WIN32_MEMORY_RANGE_ENTRY SIZE_T NumberOfBytes; } WIN32_MEMORY_RANGE_ENTRY, *PWIN32_MEMORY_RANGE_ENTRY; +typedef enum _MACHINE_ATTRIBUTES +{ + UserEnabled = 0x00000001, + KernelEnabled = 0x00000002, + Wow64Container = 0x00000004, +} MACHINE_ATTRIBUTES; + +typedef struct _PROCESS_MACHINE_INFORMATION +{ + USHORT ProcessMachine; + USHORT Res0; + MACHINE_ATTRIBUTES MachineAttributes; +} PROCESS_MACHINE_INFORMATION; + typedef enum _PROCESS_INFORMATION_CLASS { ProcessMemoryPriority, @@ -2274,6 +2288,7 @@ WINBASEAPI BOOL WINAPI GetLogicalProcessorInformationEx(LOGICAL_PROCESSOR WINBASEAPI DWORD WINAPI GetProcessHeaps(DWORD,PHANDLE); WINBASEAPI DWORD WINAPI GetProcessId(HANDLE); WINBASEAPI DWORD WINAPI GetProcessIdOfThread(HANDLE); +WINBASEAPI BOOL WINAPI GetProcessInformation(HANDLE,PROCESS_INFORMATION_CLASS,void*,DWORD); WINBASEAPI BOOL WINAPI GetProcessIoCounters(HANDLE,PIO_COUNTERS); WINBASEAPI BOOL WINAPI GetProcessPriorityBoost(HANDLE,PBOOL); WINBASEAPI BOOL WINAPI GetProcessShutdownParameters(LPDWORD,LPDWORD);