Reputation: 95
So I've been messing around with Windows API lately, and I've encountered an issue that I need a little assistance with. Actually, to be precise, there are two issues.
I will first show the code and then explain the difficulties that I am experiencing:
#pragma once
#pragma comment(lib, "Psapi.lib")
#include <stdlib.h>
#include <stdio.h>
#include <Windows.h>
#include <TlHelp32.h>
#include <Psapi.h>
void ProcessError(DWORD error);
int main() {
FILE* file = fopen("C:\\Users\\Administrator\\Desktop\\processes.txt", "w");
DWORD count, i, modulesCount;
WCHAR buffer[128] = {0};
HMODULE modules[128] = {0};
HANDLE snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, NULL);
PROCESSENTRY32 pEntry;
pEntry.dwSize = sizeof(PROCESSENTRY32);
count = 0;
if(snapshot != INVALID_HANDLE_VALUE) {
if(!Process32First(snapshot, &pEntry)) {
ProcessError(GetLastError());
CloseHandle(snapshot);
ExitProcess(EXIT_FAILURE);
}
do {
HANDLE hProc = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, pEntry.th32ProcessID);
GetModuleFileNameEx(hProc, NULL, (LPWSTR)memset(buffer, 0, 128), 128);
fwprintf(file, L"-------------------------------------------------------\n");
fwprintf(file, L"%s\t pid: %d\n", pEntry.szExeFile, pEntry.th32ProcessID);
fwprintf(file, L"%s\n", buffer);
if(hProc != INVALID_HANDLE_VALUE) {
if(EnumProcessModules(hProc, (HMODULE*)memset(modules, 0, 128), 128, &modulesCount)) {
modulesCount = modulesCount <= 128 ? modulesCount : 128;
for(i = 0; i < modulesCount; ++i) {
GetModuleFileName(modules[i], (LPWSTR)memset(buffer, 0, 128), 128);
if(wcslen(buffer) > 0) {
fwprintf(file, L"\t\t0x%X Module: %s\n", modules[i], buffer);
}
}
}
else {
ProcessError(GetLastError());
}
CloseHandle(hProc);
}
else {
ProcessError(GetLastError());
}
count++;
} while(Process32Next(snapshot, &pEntry));
fwprintf(file, L"Process count: %d\n", count);
}
else {
ProcessError(GetLastError());
CloseHandle(snapshot);
ExitProcess(EXIT_FAILURE);
}
fclose(file);
CloseHandle(snapshot);
ExitProcess(EXIT_SUCCESS);
}
void ProcessError(DWORD error) {
printf("Error in thread 0x%X, code: 0x%X\n", GetThreadId(GetCurrentThread()), error);
}
So, the first issue has to do with the following:
if(EnumProcessModules(hProc, (HMODULE*)memset(modules, 0, 128), 128, &modulesCount))
Sometimes I get an INVALID_HANDLE error, and I don't really know why. The Process handle is not invalid, nor is any other parameter passed to the function. If somebody could explain to me or at least point me in some direction (which is more preferred solution, since I am more interested to learn :D) it would do me good.
Second is that for some reason, when I enumerate process' modules and GetModuleFileName() it also includes the location of the current process.
I would get the following when I write to the file:
TuneUpUtilitiesApp32.exe pid: 2744 D:\Program Files\TuneUp Utilities 2012\TuneUpUtilitiesApp32.exe 0x76F60000 Module: C:\Windows\SYSTEM32\ntdll.dll 0x75FE0000 Module: C:\Windows\system32\kernel32.dll 0x75370000 Module: C:\Windows\system32\KERNELBASE.dll 0x761A0000 Module: C:\Windows\system32\USER32.dll 0x770D0000 Module: C:\Windows\system32\GDI32.dll 0x77130000 Module: C:\Windows\system32\LPK.dll 0x76EC0000 Module: C:\Windows\system32\USP10.dll 0x75F20000 Module: C:\Windows\system32\msvcrt.dll 0x755D0000 Module: C:\Windows\system32\ADVAPI32.dll 0x75590000 Module: C:\Windows\SYSTEM32\sechost.dll 0x757D0000 Module: C:\Windows\system32\RPCRT4.dll 0x77120000 Module: C:\Windows\system32\PSAPI.DLL 0x755B0000 Module: C:\Windows\system32\IMM32.DLL 0x75670000 Module: C:\Windows\system32\MSCTF.dll 0x10000000 Module: C:\Windows\system32\guard32.dll 0x750D0000 Module: C:\Windows\system32\VERSION.dll 0x750C0000 Module: C:\Windows\system32\fltlib.dll 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe 0x0 Module: C:\Users\Administrator\documents\visual studio 2010\Projects\FunWithWindowsAPI\Release\FunWithWindowsAPI.exe
It literally does that for every process that I can extract modules from. Any help would be much appreciated!
Upvotes: 2
Views: 2447
Reputation: 941217
You are not using the returned "modulesCount" correctly. It is not the number of modules, it is the size of the array in bytes. You'll need to divide by sizeof(HMODULE) to get the number of modules.
The second problem is that you hope that the pEntry.th32ProcessID is still valid when you start iterating the process entries. That's idle hope, a process can terminate while you are iterating. You don't check for this, you don't verify if OpenProcess() returns a valid handle. It may also fail because you don't have enough permissions to access the process.
Focus on what CreateToolhelp32Snapshot() can do, it also supports Module32First/Next(). It will be more reliable because of the function's ability to create a snapshot.
Upvotes: 1