Как получить имя/экспортный индекс символа по определенному адресу (GetProcAddress инверсия)

Предположим, у меня есть DLL, которая экспортирует некоторые функции, и я знаю адрес внутри этой DLL. Если этот адрес относится к местоположению внутри такой функции, то, при условии, что таблица экспорта отсортирована по записи функции, следующее найдет индекс этой функции в экспорте стол:

IMAGE_DOS_HEADER* dosHeader;
dosHeader = (IMAGE_DOS_HEADER*)m_handle;
unsigned int count;

if(dosHeader->e_magic != IMAGE_DOS_SIGNATURE)
{return __MODULE_ADDRESS_NOT_FOUND;}

IMAGE_NT_HEADERS* ntHeaders = (IMAGE_NT_HEADERS*)(((BYTE*)dosHeader) + dosHeader->e_lfanew);

if(ntHeaders->Signature != 0x00004550)
    {return __MODULE_ADDRESS_NOT_FOUND;}

IMAGE_OPTIONAL_HEADER* optionalHeader = &ntHeaders->OptionalHeader;
if(optionalHeader->NumberOfRvaAndSizes<IMAGE_DIRECTORY_ENTRY_EXPORT)
    {return __MODULE_ADDRESS_NOT_FOUND;}

if(optionalHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size==0)
    {return __MODULE_ADDRESS_NOT_FOUND;}

IMAGE_DATA_DIRECTORY* dataDirectory = &optionalHeader->DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT];
IMAGE_EXPORT_DIRECTORY* Exp;
Exp = (IMAGE_EXPORT_DIRECTORY*)((DWORD)dosHeader + dataDirectory->VirtualAddress);

ULONG* addressoffunctions=(ULONG*)((BYTE*) m_handle + Exp->AddressOfFunctions);

if(Exp->NumberOfNames==1)
{
    if(addressoffunctions[0] + (BYTE*)m_handle < address)
        {return 0;}
    return __MODULE_ADDRESS_NOT_FOUND;
    }

for(count = 1; count < Exp->NumberOfNames; count++)
    {
    if(addressoffunctions[count-1] + (BYTE*)m_handle >= address
    && addressoffunctions[count] + (BYTE*)m_handle < address)
        {return count-1;}
    }

, но как я могу утверждать, что адрес действительно относится к местоположению внутри экспортируемой функции.


person user877329    schedule 04.08.2011    source источник


Ответы (1)


В общем случае нельзя. Вы должны разобрать весь граф инструкций функции, чтобы получить адреса всех его инструкций.

В некоторых тривиальных случаях вы можете искать инструкцию ret, но это ненадежно.

Если вы можете выполнять статический анализ, вы можете использовать IDA для получения границ функций.

person Abyx    schedule 08.12.2011