2010-11-28 8 views
14

¿Hay alguna forma en C++/Windows para obtener la dirección base de la imagen exe/DLL? gracias :)EXE o DLL Dirección base de la imagen

+0

Se puede utilizar (además de las otras respuestas) EnumProcessModulesEx y GetModuleInformation que le permite encontrar esta información para otros procesos. – Ironside

Respuesta

14

Si carga el binario en su propio proceso, puede usar GetModuleHandle. Devuelve un HMODULE, pero eso es the same as HINSTANCE and the base address.

Si quiere saber qué dirección base prefiere el binario, debería leer el encabezado PE. Consulte here y busque el campo ImageBase en IMAGE_OPTIONAL_HEADER.

Editar: GetModuleHandle (NULL) devolverá la dirección base (aunque el tipo especificado es HMODULE) para el proceso actual.

6

Si está examinando un archivo DLL o EXE en el disco, use la utilidad dumpbin. Está instalado con Visual Studio o el SDK.

Ejemplo de salida de dumpbin /headers:

FILE HEADER VALUES 
    14C machine (i386) 
     6 number of sections 
306F7A22 time date stamp Sun Oct 01 22:35:30 1995 
     0 file pointer to symbol table 
    1D1 number of symbols 
     E0 size of optional header 
    302 characteristics 
      Executable 
      32 bit word machine 
      Debug information stripped 

OPTIONAL HEADER VALUES 
    10B magiC# 
    2.60 linker version 
    1E00 size of code 
    1E00 size of initialized data 
     0 size of uninitialized data 
    1144 address of entry point 
    1000 base of code 
    3000 base of data 
     ----- new ----- 
**2BB0000 image base** <--- This is what you are looking for 
    1000 section alignment 
    200 file alignment 
     3 subsystem (Windows CUI) 
    4.00 operating system version 
    4.00 image version 
    3.50 subsystem version 
    8000 size of image 
    400 size of headers 
    62C8 checksum 
    100000 size of stack reserve 
    1000 size of stack commit 
    100000 size of heap reserve 
    1000 size of heap commit 
     0 [  0] address [size] of Export Directory 
    5000 [  3C] address [size] of Import Directory 
    6000 [  394] address [size] of Resource Directory 
     0 [  0] address [size] of Exception Directory 
     0 [  0] address [size] of Security Directory 
    7000 [  21C] address [size] of Base Relocation Directory 
    3030 [  38] address [size] of Debug Directory 
     0 [  0] address [size] of Description Directory 
     0 [  0] address [size] of Special Directory 
     0 [  0] address [size] of Thread Storage Directory 
     0 [  0] address [size] of Load Configuration Directory 
    268 [  44] address [size] of Bound Import Directory 
    50A0 [  64] address [size] of Import Address Table Directory 
     0 [  0] address [size] of Reserved Directory 
     0 [  0] address [size] of Reserved Directory 
     0 [  0] address [size] of Reserved Directory 

SECTION HEADER #1 
    .text name 
    1D24 virtual size 
    1000 virtual address 
    1E00 size of raw data 
    400 file pointer to raw data 
     0 file pointer to relocation table 
    3C20 file pointer to line numbers 
     0 number of relocations 
    37E number of line numbers 
60000020 flags 
     Code 
     (no align specified) 
     Execute Read 
2

Si desea enumerar todos los módulos de proceso, también se puede utilizar CreateToolhelp32Snapshot:

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

std::vector<std::pair<std::string, uint32_t> > base_addresses; 
// take a snapshot of all modules in the specified process 
HANDLE snaphot_handle = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, 0); 
if (snaphot_handle != INVALID_HANDLE_VALUE) 
{ 
    // first module 
    MODULEENTRY32 mod_entry; 
    mod_entry.dwSize = sizeof(mod_entry); 
    if (Module32First(snaphot_handle, &mod_entry)) 
    { 
     // iterate through the module list of the process 
     do 
     { 
      base_addresses.push_back(
        std::make_pair(mod_entry.szModule, 
            static_cast<uint32_t>(mod_entry.modBaseAddr)); 
     } while (Module32Next(snaphot_handle, &mod_entry)); 
    } 

    CloseHandle(snaphot_handle); 
} 
3

he encontrado que la manera más conveniente y preciso para obtener del módulo dirección base (y tamaño de imagen en memoria) es a través de GetModuleInformation (incluya psapi.h, enlace a psapi.lib):

MODULEINFO module_info; memset(&module_info, 0, sizeof(module_info)); 
if (GetModuleInformation(GetCurrentProcess(), hModule, &module_info, sizeof(module_info))) { 
    DWORD module_size = module_info.SizeOfImage; 
    BYTE * module_ptr = (BYTE*)module_info.lpBaseOfDll; 
    // ... 
} 
2

Si desea obtener su propia ImageBase Dirección desde el interior de una DLL/EXE a continuación, ¿qué tal esto:

#include <winnt.h> 

EXTERN_C IMAGE_DOS_HEADER __ImageBase; 
+0

y en el depurador; puede agregar un reloj en & __ ImageBase –

0

Ponemos a tu código para encontrar Banco de Imágenes de direcciones en CPP:

#include<windows.h> 
#include<iostream> 

int main() 
{ 
    LPCSTR fileName="inputFile.exe"; 
    HANDLE hFile; 
    HANDLE hFileMapping; 
    LPVOID lpFileBase; 
    PIMAGE_DOS_HEADER dosHeader; 
    PIMAGE_NT_HEADERS peHeader; 
    PIMAGE_SECTION_HEADER sectionHeader; 

    hFile = CreateFileA(fileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,0); 

    if(hFile==INVALID_HANDLE_VALUE) 
    { 
     std::cout<<"\n CreateFile failed \n"; 
     return 1; 
    } 

    hFileMapping = CreateFileMapping(hFile,NULL,PAGE_READONLY,0,0,NULL); 

    if(hFileMapping==0) 
    { 
     std::cout<<"\n CreateFileMapping failed \n"; 
     CloseHandle(hFile); 
     return 1; 
    } 

    lpFileBase = MapViewOfFile(hFileMapping,FILE_MAP_READ,0,0,0); 

    if(lpFileBase==0) 
    { 
     std::cout<<"\n MapViewOfFile failed \n"; 
     CloseHandle(hFileMapping); 
     CloseHandle(hFile); 
     return 1; 
    } 

    dosHeader = (PIMAGE_DOS_HEADER) lpFileBase; 
    if(dosHeader->e_magic==IMAGE_DOS_SIGNATURE) 
    { 
     std::cout<<"\n DOS Signature (MZ) Matched \n"; 

     peHeader = (PIMAGE_NT_HEADERS) ((u_char*)dosHeader+dosHeader->e_lfanew); 
     if(peHeader->Signature==IMAGE_NT_SIGNATURE) 
     { 
      std::cout<<"\n PE Signature (PE) Matched \n"; 
      //once found valid exe or dll 
      std::cout<<"\n Image Base : "<<std::hex<<peHeader->OptionalHeader.ImageBase; 
     } 
     else 
     { 
      return 1; 
     } 
    } 
    else 
    { 
     return 1; 
    } 
    return 0; 
} 
Cuestiones relacionadas