Skip to content

Commit

Permalink
better module lister, better sizeofimage calculation
Browse files Browse the repository at this point in the history
  • Loading branch information
NtQuery authored and NtQuery committed Mar 17, 2014
1 parent 7611567 commit ac95c2e
Show file tree
Hide file tree
Showing 7 changed files with 102 additions and 76 deletions.
3 changes: 1 addition & 2 deletions Scylla/DumpMemoryGui.cpp
Expand Up @@ -365,7 +365,7 @@ void DumpMemoryGui::getMemoryList()
memory.protect = memBasic.Protect;


if (memory.type == MEM_MAPPED)
if (memory.type == MEM_MAPPED || memory.type == MEM_IMAGE)
{
if (!getMappedFilename(&memory))
{
Expand Down Expand Up @@ -538,7 +538,6 @@ bool DumpMemoryGui::getMappedFilename( Memory* memory )
{
WCHAR filename[MAX_PATH] = {0};

//TODO replace with Nt direct syscall
if (GetMappedFileNameW(ProcessAccessHelp::hProcess, (LPVOID)memory->address, filename, _countof(filename)) > 0)
{
return deviceNameResolver->resolveDeviceLongNameToShort(filename, memory->mappedFilename);
Expand Down
4 changes: 2 additions & 2 deletions Scylla/FunctionExport.cpp
Expand Up @@ -204,7 +204,7 @@ int WINAPI ScyllaIatSearch(DWORD dwProcessId, DWORD_PTR * iatStart, DWORD * iatS
return SCY_ERROR_PROCOPEN;
}

ProcessAccessHelp::getProcessModules(processPtr->PID, ProcessAccessHelp::moduleList);
ProcessAccessHelp::getProcessModules(ProcessAccessHelp::hProcess, ProcessAccessHelp::moduleList);

ProcessAccessHelp::selectedModule = 0;
ProcessAccessHelp::targetImageBase = processPtr->imageBase;
Expand Down Expand Up @@ -264,7 +264,7 @@ int WINAPI ScyllaIatFixAutoW(DWORD_PTR iatAddr, DWORD iatSize, DWORD dwProcessId
return SCY_ERROR_PROCOPEN;
}

ProcessAccessHelp::getProcessModules(processPtr->PID, ProcessAccessHelp::moduleList);
ProcessAccessHelp::getProcessModules(ProcessAccessHelp::hProcess, ProcessAccessHelp::moduleList);

ProcessAccessHelp::selectedModule = 0;
ProcessAccessHelp::targetImageBase = processPtr->imageBase;
Expand Down
6 changes: 3 additions & 3 deletions Scylla/MainGui.cpp
Expand Up @@ -103,7 +103,7 @@ void MainGui::InitDllStartWithPreSelect( PGUI_DLL_PARAMETER guiParam )
ProcessAccessHelp::selectedModule = &ProcessAccessHelp::moduleList.at(newSel);

ProcessAccessHelp::targetImageBase = ProcessAccessHelp::selectedModule->modBaseAddr;
ProcessAccessHelp::targetSizeOfImage = ProcessAccessHelp::getSizeOfImageProcess(ProcessAccessHelp::hProcess, ProcessAccessHelp::targetImageBase);
ProcessAccessHelp::targetSizeOfImage = ProcessAccessHelp::selectedModule->modBaseSize;

DWORD modEntryPoint = ProcessAccessHelp::getEntryPointFromFile(ProcessAccessHelp::selectedModule->fullPath);

Expand Down Expand Up @@ -531,7 +531,7 @@ void MainGui::pickDllActionHandler()
ProcessAccessHelp::selectedModule = dlgPickDll.getSelectedModule();

ProcessAccessHelp::targetImageBase = ProcessAccessHelp::selectedModule->modBaseAddr;
ProcessAccessHelp::targetSizeOfImage = ProcessAccessHelp::getSizeOfImageProcess(ProcessAccessHelp::hProcess, ProcessAccessHelp::targetImageBase);
ProcessAccessHelp::targetSizeOfImage = ProcessAccessHelp::selectedModule->modBaseSize;

DWORD modEntryPoint = ProcessAccessHelp::getEntryPointFromFile(ProcessAccessHelp::selectedModule->fullPath);

Expand Down Expand Up @@ -614,7 +614,7 @@ void MainGui::processSelectedActionHandler(int index)
return;
}

ProcessAccessHelp::getProcessModules(process.PID, ProcessAccessHelp::moduleList);
ProcessAccessHelp::getProcessModules(ProcessAccessHelp::hProcess, ProcessAccessHelp::moduleList);

apiReader.readApisFromModuleList();

Expand Down
22 changes: 16 additions & 6 deletions Scylla/NativeWinApi.h
Expand Up @@ -108,6 +108,14 @@ typedef struct _OBJECT_ATTRIBUTES
PVOID SecurityQualityOfService;
} OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES;

typedef struct _MEMORY_REGION_INFORMATION
{
PVOID AllocationBase; //Imagebase
ULONG AllocationProtect;
ULONG RegionType;
SIZE_T RegionSize; //Size of image
} MEMORY_REGION_INFORMATION, *PMEMORY_REGION_INFORMATION;

typedef enum _OBJECT_INFORMATION_CLASS {
ObjectBasicInformation,
ObjectNameInformation,
Expand Down Expand Up @@ -142,11 +150,13 @@ typedef enum _THREADINFOCLASS {
//
// Memory Information Classes for NtQueryVirtualMemory
//
typedef enum _MEMORY_INFORMATION_CLASS {
MemoryBasicInformation,
MemoryWorkingSetList,
MemorySectionName,
MemoryBasicVlmInformation
typedef enum _MEMORY_INFORMATION_CLASS
{
MemoryBasicInformation,
MemoryWorkingSetInformation,
MemoryMappedFilenameInformation, //MemorySectionName, UNICODE_STRING, Wrapper: GetMappedFileNameW
MemoryRegionInformation, //MemoryBasicVlmInformation, MEMORY_REGION_INFORMATION
MemoryWorkingSetExInformation
} MEMORY_INFORMATION_CLASS;

typedef enum _PROCESSINFOCLASS {
Expand Down Expand Up @@ -417,7 +427,7 @@ typedef NTSTATUS (WINAPI *def_NtQueryInformationFile)(HANDLE FileHandle, PIO_STA
typedef NTSTATUS (WINAPI *def_NtQueryInformationThread)(HANDLE ThreadHandle,THREADINFOCLASS ThreadInformationClass,PVOID ThreadInformation,ULONG ThreadInformationLength,PULONG ReturnLength);
typedef NTSTATUS (WINAPI *def_NtQueryInformationProcess)(HANDLE ProcessHandle,PROCESSINFOCLASS ProcessInformationClass,PVOID ProcessInformation,ULONG ProcessInformationLength,PULONG ReturnLength);
typedef NTSTATUS (WINAPI *def_NtQuerySystemInformation)(SYSTEM_INFORMATION_CLASS SystemInformationClass,PVOID SystemInformation,ULONG SystemInformationLength, PULONG ReturnLength);
typedef NTSTATUS (WINAPI *def_NtQueryVirtualMemory)(HANDLE ProcessHandle, PVOID BaseAddress, MEMORY_INFORMATION_CLASS MemoryInformationClass, PVOID Buffer, ULONG Length, PULONG ResultLength);
typedef NTSTATUS (WINAPI *def_NtQueryVirtualMemory)(HANDLE ProcessHandle, PVOID BaseAddress, MEMORY_INFORMATION_CLASS MemoryInformationClass, PVOID Buffer, SIZE_T MemoryInformationLength, PSIZE_T ReturnLength);
typedef NTSTATUS (WINAPI *def_NtOpenProcess)(PHANDLE ProcessHandle, ACCESS_MASK AccessMask, PVOID ObjectAttributes, PCLIENT_ID ClientId );
typedef NTSTATUS (WINAPI *def_NtOpenThread)(PHANDLE ThreadHandle,ACCESS_MASK DesiredAccess,POBJECT_ATTRIBUTES ObjectAttributes,PCLIENT_ID ClientId);
typedef NTSTATUS (WINAPI *def_NtResumeThread)(HANDLE ThreadHandle, PULONG SuspendCount);
Expand Down
136 changes: 76 additions & 60 deletions Scylla/ProcessAccessHelp.cpp
Expand Up @@ -650,57 +650,47 @@ DWORD ProcessAccessHelp::getProcessByName(const WCHAR * processName)
return dwPID;
}

bool ProcessAccessHelp::getProcessModules(DWORD dwPID, std::vector<ModuleInfo> &moduleList)
bool ProcessAccessHelp::getProcessModules(HANDLE hProcess, std::vector<ModuleInfo> &moduleList)
{
HANDLE hModuleSnap = INVALID_HANDLE_VALUE;
MODULEENTRY32 me32;
ModuleInfo module;
ModuleInfo module;
WCHAR filename[MAX_PATH*2] = {0};
DWORD cbNeeded = 0;
bool retVal = false;
DeviceNameResolver deviceNameResolver;

// Take a snapshot of all modules in the specified process.
hModuleSnap = CreateToolhelp32Snapshot( TH32CS_SNAPMODULE, dwPID );
if( hModuleSnap == INVALID_HANDLE_VALUE )
{
return false;
}

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

// Retrieve information about the first module,
// and exit if unsuccessful
if( !Module32First( hModuleSnap, &me32 ) )
{
CloseHandle( hModuleSnap );
return false;
}

// Now walk the module list of the process,
// and display information about each module

//the first is always the .exe
if (!Module32Next(hModuleSnap, &me32))
{
CloseHandle( hModuleSnap );
return false;
}
moduleList.reserve(20);

moduleList.reserve(20);
EnumProcessModules(hProcess, 0, 0, &cbNeeded);

do
{
//printf(L"\n MODULE NAME: %s", me32.szModule);
module.modBaseAddr = (DWORD_PTR)me32.modBaseAddr;
module.modBaseSize = me32.modBaseSize;
module.isAlreadyParsed = false;
module.parsing = false;
wcscpy_s(module.fullPath, me32.szExePath);
HMODULE* hMods=(HMODULE*)malloc(cbNeeded*sizeof(HMODULE));

moduleList.push_back(module);
if (hMods)
{
if(EnumProcessModules(hProcess, hMods, cbNeeded, &cbNeeded))
{
for(unsigned int i = 1; i < (cbNeeded/sizeof(HMODULE)); i++) //skip first module!
{
module.modBaseAddr = (DWORD_PTR)hMods[i];
module.modBaseSize = (DWORD)getSizeOfImageProcess(hProcess, module.modBaseAddr);
module.isAlreadyParsed = false;
module.parsing = false;

filename[0] = 0;
if (GetMappedFileNameW(hProcess, (LPVOID)module.modBaseAddr, filename, _countof(filename)) > 0)
{
deviceNameResolver.resolveDeviceLongNameToShort(filename, module.fullPath);
}

moduleList.push_back(module);
}

retVal = true;
}

} while(Module32Next(hModuleSnap, &me32));
free(hMods);
}

CloseHandle( hModuleSnap );
return true;
return retVal;
}

bool ProcessAccessHelp::getMemoryRegionFromAddress(DWORD_PTR address, DWORD_PTR * memoryRegionBase, SIZE_T * memoryRegionSize)
Expand Down Expand Up @@ -739,38 +729,52 @@ bool ProcessAccessHelp::getSizeOfImageCurrentProcess()

SIZE_T ProcessAccessHelp::getSizeOfImageProcess(HANDLE processHandle, DWORD_PTR moduleBase)
{
SIZE_T sizeOfImage = 0;
SIZE_T sizeOfImage = 0, sizeOfImageNative = 0;
MEMORY_BASIC_INFORMATION lpBuffer = {0};
SIZE_T dwLength = sizeof(MEMORY_BASIC_INFORMATION);

sizeOfImageNative = getSizeOfImageProcessNative(processHandle, moduleBase);

if (sizeOfImageNative)
{
return sizeOfImageNative;
}

WCHAR filenameOriginal[MAX_PATH*2] = {0};
WCHAR filenameTest[MAX_PATH*2] = {0};

GetMappedFileNameW(processHandle, (LPVOID)moduleBase, filenameOriginal, _countof(filenameOriginal));

do
{
moduleBase = (DWORD_PTR)((SIZE_T)moduleBase + lpBuffer.RegionSize);
sizeOfImage += lpBuffer.RegionSize;

//printf("Query 0x"PRINTF_DWORD_PTR_FULL" size 0x%08X\n",moduleBase,sizeOfImage);

if (!VirtualQueryEx(processHandle, (LPCVOID)moduleBase, &lpBuffer, dwLength))
if (!VirtualQueryEx(processHandle, (LPCVOID)moduleBase, &lpBuffer, sizeof(MEMORY_BASIC_INFORMATION)))
{
#ifdef DEBUG_COMMENTS
Scylla::debugLog.log(L"getSizeOfImageProcess :: VirtualQuery failed %X", GetLastError());
#endif
lpBuffer.Type = 0;
sizeOfImage = 0;
}
/*else
{
printf("\nAllocationBase %X\n",lpBuffer.AllocationBase);
printf("AllocationProtect %X\n",lpBuffer.AllocationProtect);
printf("BaseAddress %X\n",lpBuffer.BaseAddress);
printf("Protect %X\n",lpBuffer.Protect);
printf("RegionSize %X\n",lpBuffer.RegionSize);
printf("State %X\n",lpBuffer.State);
printf("Type %X\n",lpBuffer.Type);
}*/

GetMappedFileNameW(processHandle, (LPVOID)moduleBase, filenameTest, _countof(filenameTest));

if (_wcsicmp(filenameOriginal,filenameTest) != 0)//problem: 2 modules without free space
{
break;
}

} while (lpBuffer.Type == MEM_IMAGE);

//printf("Real sizeOfImage %X\n",sizeOfImage);

//if (sizeOfImage != sizeOfImageNative)
//{
// WCHAR temp[1000] = {0};
// wsprintfW(temp, L"0x%X sizeofimage\n0x%X sizeOfImageNative", sizeOfImage, sizeOfImageNative);
// MessageBoxW(0, temp, L"Test", 0);
//}

return sizeOfImage;
}
Expand Down Expand Up @@ -911,4 +915,16 @@ bool ProcessAccessHelp::isPageExecutable( DWORD Protect )
return false;
}

}
}

SIZE_T ProcessAccessHelp::getSizeOfImageProcessNative( HANDLE processHandle, DWORD_PTR moduleBase )
{
MEMORY_REGION_INFORMATION memRegion = {0};
SIZE_T retLen = 0;
if (NativeWinApi::NtQueryVirtualMemory(processHandle, (PVOID)moduleBase, MemoryRegionInformation, &memRegion, sizeof(MEMORY_REGION_INFORMATION), &retLen) == STATUS_SUCCESS)
{
return memRegion.RegionSize;
}

return 0;
}
3 changes: 2 additions & 1 deletion Scylla/ProcessAccessHelp.h
Expand Up @@ -124,7 +124,7 @@ class ProcessAccessHelp
/*
* Get all modules from a process
*/
static bool getProcessModules(DWORD dwPID, std::vector<ModuleInfo> &moduleList);
static bool getProcessModules(HANDLE hProcess, std::vector<ModuleInfo> &moduleList);


/*
Expand Down Expand Up @@ -225,4 +225,5 @@ class ProcessAccessHelp
static bool resumeProcess();
static bool terminateProcess();
static bool isPageExecutable( DWORD Protect );
static SIZE_T getSizeOfImageProcessNative( HANDLE processHandle, DWORD_PTR moduleBase );
};
4 changes: 2 additions & 2 deletions Scylla/Scylla.cpp
Expand Up @@ -27,7 +27,7 @@ void Scylla::initAsGuiApp()
processLister.setDebugPrivileges();
}

ProcessAccessHelp::getProcessModules(GetCurrentProcessId(), ProcessAccessHelp::ownModuleList);
ProcessAccessHelp::getProcessModules(GetCurrentProcess(), ProcessAccessHelp::ownModuleList);
}

void Scylla::initAsDll()
Expand All @@ -36,5 +36,5 @@ void Scylla::initAsDll()

NativeWinApi::initialize();
SystemInformation::getSystemInformation();
ProcessAccessHelp::getProcessModules(GetCurrentProcessId(), ProcessAccessHelp::ownModuleList);
ProcessAccessHelp::getProcessModules(GetCurrentProcess(), ProcessAccessHelp::ownModuleList);
}

0 comments on commit ac95c2e

Please sign in to comment.