如何在 C++ 中按名称获取进程句柄?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/865152/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-27 17:39:13  来源:igfitidea点击:

How can I get a process handle by its name in C++?

c++winapiprocess

提问by Malfist

I'm trying to get the process handle of, say example.exe, so I can call TerminateProcesson it. How can I do this? Notice, it doesn't have a window so FindWindowwon't work.

我正在尝试获取例如 example.exe 的进程句柄,以便我可以调用TerminateProcess它。我怎样才能做到这一点?请注意,它没有窗口,因此FindWindow无法使用。

回答by xian

#include <cstdio>
#include <windows.h>
#include <tlhelp32.h>

int main( int, char *[] )
{
    PROCESSENTRY32 entry;
    entry.dwSize = sizeof(PROCESSENTRY32);

    HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);

    if (Process32First(snapshot, &entry) == TRUE)
    {
        while (Process32Next(snapshot, &entry) == TRUE)
        {
            if (stricmp(entry.szExeFile, "target.exe") == 0)
            {  
                HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, entry.th32ProcessID);

                // Do stuff..

                CloseHandle(hProcess);
            }
        }
    }

    CloseHandle(snapshot);

    return 0;
}

Also, if you'd like to use PROCESS_ALL_ACCESS in OpenProcess, you could try this:

另外,如果你想在 OpenProcess 中使用 PROCESS_ALL_ACCESS,你可以试试这个:

#include <cstdio>
#include <windows.h>
#include <tlhelp32.h>

void EnableDebugPriv()
{
    HANDLE hToken;
    LUID luid;
    TOKEN_PRIVILEGES tkp;

    OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken);

    LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &luid);

    tkp.PrivilegeCount = 1;
    tkp.Privileges[0].Luid = luid;
    tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

    AdjustTokenPrivileges(hToken, false, &tkp, sizeof(tkp), NULL, NULL);

    CloseHandle(hToken); 
}

int main( int, char *[] )
{
    EnableDebugPriv();

    PROCESSENTRY32 entry;
    entry.dwSize = sizeof(PROCESSENTRY32);

    HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);

    if (Process32First(snapshot, &entry) == TRUE)
    {
        while (Process32Next(snapshot, &entry) == TRUE)
        {
            if (stricmp(entry.szExeFile, "target.exe") == 0)
            {  
                HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, entry.th32ProcessID);

                // Do stuff..

                CloseHandle(hProcess);
            }
        }
    }

    CloseHandle(snapshot);

    return 0;
}

回答by Michael

The following code shows how you can use toolhelp and OpenProcess to get a handle to the process. Error handling removed for brevity.

以下代码显示了如何使用 toolhelp 和 OpenProcess 来获取进程的句柄。为简洁起见,删除了错误处理。

HANDLE GetProcessByName(PCSTR name)
{
    DWORD pid = 0;

    // Create toolhelp snapshot.
    HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
    PROCESSENTRY32 process;
    ZeroMemory(&process, sizeof(process));
    process.dwSize = sizeof(process);

    // Walkthrough all processes.
    if (Process32First(snapshot, &process))
    {
        do
        {
            // Compare process.szExeFile based on format of name, i.e., trim file path
            // trim .exe if necessary, etc.
            if (string(process.szExeFile) == string(name))
            {
               pid = process.th32ProcessID;
               break;
            }
        } while (Process32Next(snapshot, &process));
    }

    CloseHandle(snapshot);

    if (pid != 0)
    {
         return OpenProcess(PROCESS_ALL_ACCESS, FALSE, pid);
    }

    // Not found


       return NULL;
}

回答by Rob Kennedy

There are two basic techniques. The first uses PSAPI; MSDN has an examplethat uses EnumProcesses, OpenProcess, EnumProcessModules, and GetModuleBaseName.

有两种基本技术。第一种使用PSAPI;MSDN有一个例子,使用EnumProcessesOpenProcessEnumProcessModules,和GetModuleBaseName

The other uses Toolhelp, which I prefer. Use CreateToolhelp32Snapshotto get a snapshot of the process list, walk over it with Process32Firstand Process32Next, which provides module name and process ID, until you find the one you want, and then call OpenProcessto get a handle.

另一个使用我更喜欢的 Toolhelp。使用CreateToolhelp32Snapshot获得进程列表的快照,走在它与Process32FirstProcess32Next,它提供了模块名称和进程ID,直到你找到你想要的,然后调用OpenProcess得到的句柄。

回答by BullyWiiPlaza

The following code can be used:

可以使用以下代码:

DWORD FindProcessId(const std::wstring& processName)
{
    PROCESSENTRY32 processInfo;
    processInfo.dwSize = sizeof(processInfo);

    HANDLE processesSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);
    if (processesSnapshot == INVALID_HANDLE_VALUE) {
        return 0;
    }

    Process32First(processesSnapshot, &processInfo);
    if (!processName.compare(processInfo.szExeFile))
    {
        CloseHandle(processesSnapshot);
        return processInfo.th32ProcessID;
    }

    while (Process32Next(processesSnapshot, &processInfo))
    {
        if (!processName.compare(processInfo.szExeFile))
        {
            CloseHandle(processesSnapshot);
            return processInfo.th32ProcessID;
        }
    }

    CloseHandle(processesSnapshot);
    return 0;
}

Usage:

用法:

auto processId = FindProcessId(L"blabla.exe");

Getting a handle should be obvious, just call OpenProcess()or similar on it.

获取句柄应该很明显,只需调用OpenProcess()或类似方法即可。

回答by Lloyd

Check out: MSDN Article

查看:MSDN 文章

You can use GetModuleName(I think?) to get the name and check against that.

您可以使用GetModuleName(我认为?)来获取名称并进行检查。

回答by aJ.

OpenProcessFunction

OpenProcess函数

From MSDN:

来自 MSDN:

To open a handle to another local process and obtain full access rights, you must enable the SeDebugPrivilege privilege.

要打开另一个本地进程的句柄并获得完全访问权限,您必须启用 SeDebugPrivilege 权限。