未初始化的读错误

时间:2016-05-23 12:39:43

标签: c++

我编写了一个方法来获取c ++项目中的所有进程ID。

Int CProcessHelper::GetAllPIDs(const char *processName, _STL_NAMESPACE_::vector<DWORD> &pids)
{  
HANDLE hProcessSnap;
PROCESSENTRY32 pe32;
HANDLE hProcess;
BOOL bContinue;

pids.clear();
// Take a snapshot of all processes in the system.
hProcessSnap = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );
if( hProcessSnap == INVALID_HANDLE_VALUE )
{
    return 0;
}

// Set the size of the structure before using it.
pe32.dwSize = sizeof( PROCESSENTRY32 );

// Retrieve information about the first process,
// and exit if unsuccessful
bContinue = Process32First( hProcessSnap, &pe32 );

while(bContinue)
{
    hProcess = OpenProcess(PROCESS_QUERY_INFORMATION|PROCESS_VM_READ, FALSE, pe32.th32ProcessID);
    if( hProcess != NULL )
    {
        TCHAR szModName[MAX_PATH];

        // Get the full path to the module's file.
        if(GetModuleFileNameEx( hProcess, NULL, szModName,
                                  sizeof(szModName)))
        {
            char *ptr = strrchr(szModName, '\\');
            if( (ptr && stricmp(ptr+1, processName) == 0) ||
                stricmp(szModName, processName) == 0)
            {
                pids.push_back(pe32.th32ProcessID);
                /*CloseHandle( hProcess );
                pid = pe32.th32ProcessID;
                break;*/
            }
        }
        CloseHandle( hProcess );
    }
    bContinue = Process32Next( hProcessSnap, &pe32 );
}
CloseHandle( hProcessSnap );
return (int) pids.size();
}

当我在Dr Memory下运行此代码时,我正在关注&#34;未初始化的读取&#34;错误:

Uninitialized Read Error 1

在这一行:

if(GetModuleFileNameEx( hProcess, NULL, szModName,
                                      sizeof(szModName)))

第二个错误是:

Uninitialized Read Error 2

在这一行 -

bContinue = Process32First( hProcessSnap, &pe32 );

我没有得到记忆博士报告我这些错误。这些只是假阳性错误吗?

请帮我确定哪个部分未初始化。

如果你仔细查看附带的Dr Memory错误截图,你会发现两个错误都调用了

KERNELBASE.dll!WideCharToMultiByte

因为我使用的是TCHAR(1.e的char类型,而不是WCHAR类型(宽字符))用于szFileName var。

TCHAR szModName[MAX_PATH];

我不知道为什么它调用WideCharToMultiByte()方法,因为我使用的方法接受char类型而不是宽字符类型。

1 个答案:

答案 0 :(得分:0)

hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, pe32.th32ProcessID);

pe32.th32ProcessID尚未设置,它是未初始化的内存。出于您的目的,也不需要OpenProcess()。

if (GetModuleFileNameEx(hProcess, NULL, szModName, sizeof(szModName)))

此功能不是必需的,可执行文件的名称由PROCESSENTRY32结构公开。另外,最后一个参数应该使用strlen而不是sizeof,因为您要的是字符数而不是缓冲区的大小。

此代码还存在其他问题,而不是试图重蹈覆辙,MSDN拥有完整的注释源代码,可使用ToolHelp32Snapshot函数集合来完成您想做的事情,您可以找到它{{3} }。

这是一个简洁的示例,我已对其进行了修改以使其完全符合您的需求:

#include <windows.h>
#include <iostream>
#include <vector>
#include <TlHelp32.h>
#include <Psapi.h>

int GetAllPIDs(const char* processName, std::vector<DWORD>& pids)
{
    HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
    if (hSnap != INVALID_HANDLE_VALUE)
    {
        PROCESSENTRY32 procEntry;
        procEntry.dwSize = sizeof(procEntry);

        if (Process32First(hSnap, &procEntry))
        {
            do
            {
                if (!_stricmp(procEntry.szExeFile, processName))
                {
                    pids.push_back(procEntry.th32ProcessID);
                }
            } while (Process32Next(hSnap, &procEntry));

        }
    }
    CloseHandle(hSnap);

    return (int)pids.size();
}

int main()
{
    std::vector<DWORD> piddies;

    GetAllPIDs("calc.exe", piddies);

    for (auto p : piddies)
    {
        std::cout << "0x" << std::hex << p << std::endl;
    }

    std::getchar();

    return 0;
}