当程序可见或最小化时进程 ID 发生变化
Process ID changes when program is visible or minimized
我正在尝试获取程序的进程 ID (PID),但由于某些奇怪的原因,PID 发生了变化。当目标程序 (Alarms & Clock
) 可见时,它给了我错误的 PID,而将程序最小化给了我正确的 PID。
我猜测最小化目标程序 suspends
它正在处理,从而允许读取它。但是,即使进程是 运行.
,简单地读取 PID 也不应该是一个限制。
有人知道我做错了什么吗?
目前尝试过的方法:
- 运行 在管理模式下
- 为 64 位编译
- 为 32 位编译
有一段描述问题的简洁有效的代码:
#include <iostream>
#include <Windows.h>
#include <string>
int main()
{
std::string window_name = "Alarms & Clock"; //Feel free to replace this with another program
HWND hwnd = FindWindowA(NULL, window_name.c_str());
if (!hwnd)
{
std::cerr << "Error: Could not find window" << std::endl;
return -1;
}
DWORD processID = 0;
GetWindowThreadProcessId(hwnd, &processID);
std::cout << "Process ID: " << processID << std::endl;
std::cin.get();
return 0;
}
您需要检查返回的 hwnd 值 - 您可以查看当 appcontainer 应用程序暂停时(您将其最小化 window)以及当它处于活动状态时 - 您会有所不同hwnd。对于处于 活动状态 的所有应用程序容器 - 它的主框架 window 不属于它的进程,而是属于 ApplicationFrameHost.exe 并且有ApplicationFrameWindowclass。但是当它最小化时 - 需要准确点击最小化按钮 - 进程 暂停 并且..但是让 运行 此代码
if (HWND hwnd = FindWindowW(0, L"Alarms & Clock"))
{
ULONG pid, tid = GetWindowThreadProcessId(hwnd, &pid);
DbgPrint("%x %x.%x", hwnd, pid, tid);
WCHAR sz[MAX_PATH];
if (GetClassName(hwnd, sz, RTL_NUMBER_OF(sz)))
{
DbgPrint(" [%S]", sz);
}
if (HANDLE hProcess = OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, FALSE, pid))
{
PROCESS_EXTENDED_BASIC_INFORMATION pebi;
if (0 <= ZwQueryInformationProcess(hProcess, ProcessBasicInformation, &pebi, sizeof(pebi), 0))
{
DbgPrint(" Suspended=%x, flags(%x)", pebi.IsFrozen, pebi.Flags);
}
ULONG len = RTL_NUMBER_OF(sz);
if (QueryFullProcessImageNameW(hProcess, 0, sz, &len))
{
DbgPrint(" %S", sz);
}
CloseHandle(hProcess);
}
DbgPrint("\n");
}
我得到了 2 个状态的下一个输出:
1902e6 510.155c [Windows.UI.Core.CoreWindow] Suspended=1, flags(58) C:\Program Files\WindowsApps\Microsoft.WindowsAlarms_10.1605.1742.0_x64__8wekyb3d8bbwe\Time.exe
740414 574.934 [ApplicationFrameWindow] Suspended=0, flags(8) C:\Windows\System32\ApplicationFrameHost.exe
我能够使用 GCC 5.3 在 Win/10 上重新生成问题。我使用 "Calculator" 应用程序对其进行了测试。当应用程序的 window 被 not 最小化时,我得到了属于 ApplicationFrameHost.exe 的 PID = 14440,但是,我得到了 PID = 1936 当 calc 的 window 最小化时正确。
这是因为 "Calculator" 是 tablet 应用程序,而不是 desktop 应用程序。 桌面 无论window 是否最小化,应用程序都会提供正确的 PID。
我认为 对您有用。
ApplicationFrameHost.exe似乎是一个处理许多子应用程序的应用程序容器。需要额外的代码来检索您要查找的确切子应用程序 pid。
基于该页面,我编写了这段代码并且对我有用,但是,您可能需要改进它。
typedef struct {
DWORD ownerpid;
DWORD childpid;
} windowinfo;
BOOL CALLBACK EnumChildWindowsCallback(HWND hWnd, LPARAM lp) {
windowinfo* info = (windowinfo*)lp;
DWORD pid = 0;
GetWindowThreadProcessId(hWnd, &pid);
if (pid != info->ownerpid) info->childpid = pid;
return TRUE;
}
void Show_PID()
{
Sleep(1000);
std::string window_name = "Calculator";
HWND hwnd = FindWindowA(NULL, window_name.c_str());
windowinfo info = { 0 };
GetWindowThreadProcessId(hwnd, &info.ownerpid);
info.childpid = info.ownerpid;
EnumChildWindows(hwnd, EnumChildWindowsCallback, (LPARAM)&info);
std::cout << "Process ID: " << info.childpid << std::endl;
}
int main()
{
for (int i = 0; i < 9; ++i)
{
Show_PID();
}
return 0;
}
我正在尝试获取程序的进程 ID (PID),但由于某些奇怪的原因,PID 发生了变化。当目标程序 (Alarms & Clock
) 可见时,它给了我错误的 PID,而将程序最小化给了我正确的 PID。
我猜测最小化目标程序 suspends
它正在处理,从而允许读取它。但是,即使进程是 运行.
有人知道我做错了什么吗?
目前尝试过的方法:
- 运行 在管理模式下
- 为 64 位编译
- 为 32 位编译
有一段描述问题的简洁有效的代码:
#include <iostream>
#include <Windows.h>
#include <string>
int main()
{
std::string window_name = "Alarms & Clock"; //Feel free to replace this with another program
HWND hwnd = FindWindowA(NULL, window_name.c_str());
if (!hwnd)
{
std::cerr << "Error: Could not find window" << std::endl;
return -1;
}
DWORD processID = 0;
GetWindowThreadProcessId(hwnd, &processID);
std::cout << "Process ID: " << processID << std::endl;
std::cin.get();
return 0;
}
您需要检查返回的 hwnd 值 - 您可以查看当 appcontainer 应用程序暂停时(您将其最小化 window)以及当它处于活动状态时 - 您会有所不同hwnd。对于处于 活动状态 的所有应用程序容器 - 它的主框架 window 不属于它的进程,而是属于 ApplicationFrameHost.exe 并且有ApplicationFrameWindowclass。但是当它最小化时 - 需要准确点击最小化按钮 - 进程 暂停 并且..但是让 运行 此代码
if (HWND hwnd = FindWindowW(0, L"Alarms & Clock"))
{
ULONG pid, tid = GetWindowThreadProcessId(hwnd, &pid);
DbgPrint("%x %x.%x", hwnd, pid, tid);
WCHAR sz[MAX_PATH];
if (GetClassName(hwnd, sz, RTL_NUMBER_OF(sz)))
{
DbgPrint(" [%S]", sz);
}
if (HANDLE hProcess = OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, FALSE, pid))
{
PROCESS_EXTENDED_BASIC_INFORMATION pebi;
if (0 <= ZwQueryInformationProcess(hProcess, ProcessBasicInformation, &pebi, sizeof(pebi), 0))
{
DbgPrint(" Suspended=%x, flags(%x)", pebi.IsFrozen, pebi.Flags);
}
ULONG len = RTL_NUMBER_OF(sz);
if (QueryFullProcessImageNameW(hProcess, 0, sz, &len))
{
DbgPrint(" %S", sz);
}
CloseHandle(hProcess);
}
DbgPrint("\n");
}
我得到了 2 个状态的下一个输出:
1902e6 510.155c [Windows.UI.Core.CoreWindow] Suspended=1, flags(58) C:\Program Files\WindowsApps\Microsoft.WindowsAlarms_10.1605.1742.0_x64__8wekyb3d8bbwe\Time.exe
740414 574.934 [ApplicationFrameWindow] Suspended=0, flags(8) C:\Windows\System32\ApplicationFrameHost.exe
我能够使用 GCC 5.3 在 Win/10 上重新生成问题。我使用 "Calculator" 应用程序对其进行了测试。当应用程序的 window 被 not 最小化时,我得到了属于 ApplicationFrameHost.exe 的 PID = 14440,但是,我得到了 PID = 1936 当 calc 的 window 最小化时正确。
这是因为 "Calculator" 是 tablet 应用程序,而不是 desktop 应用程序。 桌面 无论window 是否最小化,应用程序都会提供正确的 PID。
我认为
ApplicationFrameHost.exe似乎是一个处理许多子应用程序的应用程序容器。需要额外的代码来检索您要查找的确切子应用程序 pid。
基于该页面,我编写了这段代码并且对我有用,但是,您可能需要改进它。
typedef struct {
DWORD ownerpid;
DWORD childpid;
} windowinfo;
BOOL CALLBACK EnumChildWindowsCallback(HWND hWnd, LPARAM lp) {
windowinfo* info = (windowinfo*)lp;
DWORD pid = 0;
GetWindowThreadProcessId(hWnd, &pid);
if (pid != info->ownerpid) info->childpid = pid;
return TRUE;
}
void Show_PID()
{
Sleep(1000);
std::string window_name = "Calculator";
HWND hwnd = FindWindowA(NULL, window_name.c_str());
windowinfo info = { 0 };
GetWindowThreadProcessId(hwnd, &info.ownerpid);
info.childpid = info.ownerpid;
EnumChildWindows(hwnd, EnumChildWindowsCallback, (LPARAM)&info);
std::cout << "Process ID: " << info.childpid << std::endl;
}
int main()
{
for (int i = 0; i < 9; ++i)
{
Show_PID();
}
return 0;
}