替代Windows 2000的GetProcessID

时间:2008-11-07 13:17:09

标签: c++ windows winapi

我使用GetProcessID意外删除了应用程序的Win2K兼容性。

我像这样使用它来获取已启动应用程序的主要HWND。

ShellExecuteEx(&info); // Launch application
HANDLE han = info.hProcess; // Get process

cbinfo.han = han;

//Call EnumWindows to enumerate windows....
//with this as the callback

static BOOL CALLBACK enumproc(HWND hwnd, LPARAM lParam)
{
  DWORD id;
  GetWIndowThreadProcessID(hwnd, &id);
  if (id == GetProcessID(cbinfo.han))
    setResult(hwnd)
 ...
}

任何想法如何在Win2K上实现相同的功能?

4 个答案:

答案 0 :(得分:6)

有一种'不支持的'功能:ZwQueryInformationProcess():见

http://msdn.microsoft.com/en-us/library/ms687420.aspx

给定句柄,这将为您提供进程ID(以及其他内容)。这不能保证适用于未来的Windows版本,因此我建议使用一个帮助函数来测试操作系统版本,然后使用GetProcAddress()为XP及更高版本调用GetProcessId(),并仅为Win2K调用ZwQueryInformationProcess()

答案 1 :(得分:5)

DavidK是对的。请参阅ZwQueryInformationProcess文档中的注释:

  

[ZwQueryInformationProcess可能是   将来改变或不可用   Windows版本。应用   应该使用备用功能   本主题中列出的内容。]

这意味着Microsoft可以选择在将来的任何时候删除它,从而破坏您的应用程序。我强烈认为你遵循DavidK的建议并在操作系统上使用不支持GetProcessID的ZwQueryInformationProcess,并在支持它的操作系统上使用GetProcessID(XP SP1及更高版本)。

答案 2 :(得分:3)

感谢DavidK和Larry - 这是我的最终解决方案。完整的错误处理留给读者练习。

请注意,我不是专门检查操作系统版本,而是尝试动态链接到这些功能。静态链接意味着如果程序不可用,应用程序将无法加载。

已经在Win2K和Vista上成功尝试过:

#include "Winternl.h"

typedef DWORD (WINAPI* pfnGetProcID)(HANDLE h);

typedef NTSTATUS (WINAPI* pfnQueryInformationProcess)(
    HANDLE ProcessHandle,
    PROCESSINFOCLASS ProcessInformationClass,
    PVOID ProcessInformation,
    ULONG ProcessInformationLength,
    PULONG ReturnLength);

DWORD MyGetProcessId(HANDLE h)
{
    static pfnQueryInformationProcess ntQIP = (pfnQueryInformationProcess) GetProcAddress(GetModuleHandle("NTDLL.DLL"),"NtQueryInformationProcess");
    static pfnGetProcID getPId  = (pfnGetProcID) GetProcAddress(GetModuleHandle("KERNEL32.DLL"),"GetProcessId");

    if ((ntQIP == NULL) && (getPId == NULL))
        throw Exception("Can't retrieve process ID : GetProcessID not supported");

    if (getPId != NULL)
        return getPId(h);
    else
    {
        PROCESS_BASIC_INFORMATION info;
        ULONG returnSize;
        ntQIP(h, ProcessBasicInformation, &info, sizeof(info), &returnSize);  // Get basic information.
        return info.UniqueProcessId;
    }
}

答案 3 :(得分:-1)

不,这不是ZwQueryInformationProcess() 它是NtQIP,当然它适用于自NT 3.5以来的所有版本,你根本不需要测试操作系统