计算由其className运行的程序

时间:2019-07-14 20:21:11

标签: c++ winapi

我正在尝试检测正在运行一个应用程序实例的实例。他有没有打开我的申请一次?两次?三次? 我试图通过按进程名称检查其实例来检测它,但是在Windows中它是尖尖的-人们可能会更改.exe名称,并且它不会计入最终编号。

那我该如何进行?我曾考虑过按className(HWND?)而不是processName进行搜索,但是我该怎么做?

这是我用来按进程名称检测的代码:

int Platform::getMulticlientCount(const std::string& ProcessName)
{
    PROCESSENTRY32 pe32 = { sizeof(PROCESSENTRY32) };
    HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
    const char *cstr = ProcessName.c_str();
    int counter = 0;
    if (Process32First(hSnapshot, &pe32))
    {
        do
        {
            if (_tcsicmp(pe32.szExeFile, cstr) == 0)
            {
                counter++;
            }
        } while (Process32Next(hSnapshot, &pe32));
    }

    CloseHandle(hSnapshot);
    return counter;
}

2 个答案:

答案 0 :(得分:0)

这是一个示例代码,用于计算正在运行的实例。当应用程序对实例本身进行计数时,是否重命名二进制文件并不重要。我使用了一个文件来简化示例,但是注册表也可以工作。唯一缺少的是全局互斥锁,以防止文件被并发访问。 HTH

#include <iostream>
#include <thread>
#include <fstream>

#include <Windows.h>

class GlobalCounter
{
public:
    GlobalCounter(const std::string& id)
    : _id(id)
    {
        const auto filename = "C:\\users\\twollgam\\" + id + ".counter";

        if (GlobalFindAtomA(id.c_str()) == 0)
        {
            std::ofstream(filename) << 1;

            std::cout << "I am the first instance." << std::endl;
        }
        else
        {
            auto counter = 0;

            std::ifstream(filename) >> counter;

            ++counter;

            std::ofstream(filename) << counter;

            std::cout << "I am the " << counter << " instance." << std::endl;
        }

        _atom = GlobalAddAtomA(id.c_str());
    }

    ~GlobalCounter()
    {
        const auto filename = "C:\\users\\twollgam\\" + _id + ".counter";
        auto counter = 0;

        std::ifstream(filename) >> counter;

        --counter;

        std::ofstream(filename) << counter;

        GlobalDeleteAtom(_atom);
    }

private:
    const std::string _id;
    ATOM _atom;
};

int main()
{
    const auto globalCounter = GlobalCounter("test");

    std::cout << "Hello World!\n";

    std::this_thread::sleep_for(std::chrono::seconds(30));

    return 0;
}

答案 1 :(得分:0)

雷米人的实例:

static int counter;
BOOL CALLBACK EnumWindowsProc(HWND hwnd, LPARAM lParam)
{

    char classname[MAX_PATH] = { 0 };
    GetClassNameA(hwnd,classname, MAX_PATH);
    if (_tcsicmp(classname, (char*)lParam) == 0)
        counter++;
    return true;
}
int Platform::getMulticlientCount(const std::string& ClassName)
{
    counter = 0;
    const char *cstr = ClassName.c_str();
    EnumWindows(EnumWindowsProc, (LPARAM)cstr);
    return counter;
}

如果还需要获取实例,请在EnumWindowsProc中:

HINSTANCE instance = (HINSTANCE)GetWindowLongPtr(hwnd, GWLP_HINSTANCE);

如果还需要获取processId,请在EnumWindowsProc中:

DWORD pid;
GetWindowThreadProcessId(hwnd, &pid);