hasherezade / exe_to_dll

Converts a EXE into DLL
1.25k stars 188 forks source link

memory load module #2

Closed nblog closed 4 years ago

nblog commented 4 years ago

LoadLibraryA

I tried to replace "LoadLibraryA" with a memory load module and found it failed.

my code:

size_t v_size = 0;
PBYTE loaded_pe = peconv::load_pe_executable(file.c_str(), v_size);
if (NULL == loaded_pe) {
    return FALSE;
}

// calculate the Entry Point of the manually loaded module
DWORD ep_rva = (0 == rva_ep) ? peconv::get_entry_point_rva(loaded_pe) : rva_ep;
ULONG_PTR ep_va = ep_rva + (ULONG_PTR)loaded_pe;
if (NULL == ep_rva || NULL == ep_va) {
    return FALSE;
}

typedef int(APIENTRY* fnMainCRTStartup)();
fnMainCRTStartup AddressOfEntryPoint = (fnMainCRTStartup)ep_va;
if (AddressOfEntryPoint) {
    auto result = AddressOfEntryPoint();
}
hasherezade commented 4 years ago

@nblog - First at all, what was your error? And when it happened? At loading time? At execution time? I can see that you want to call a DLL, but using an entry point whisch is from EXE - it is not correct. The Entry Point from a DLL is DllMain:

BOOL WINAPI DllMain(
  _In_ HINSTANCE hinstDLL,
  _In_ DWORD     fdwReason,
  _In_ LPVOID    lpvReserved
);

Also, this app is especially for testing the DLLs converted by exe_to_dll. And in this case, we just want to call the original Entry Point, that was there before the conversion. You cannot fetch it from the headers, because it is already overwritten. That's why you need to supply it as an argument. So, the <Entry Point RVA> - means the Entry Point that your EXE had before the conversion. It is not the same as your current Entry Point.

nblog commented 4 years ago

I made it. thank you.

For better compatibility, I made a little modification Before entering "new_main()" I modified "PEB.ImageBaseAddress" to point to "memory exe imagebase" Therefore, it will not return "testload.exe" imagebase because of GetModuleHandle(NULL,....) inside the program

image

hasherezade commented 4 years ago

Sure, you can do it if it fits your particular scenario. BTW - the way you used to retrieve PEB will work only for 32 bit applications. If you want it to work for both 32 and 64 you can use this way