Win32 API to enumerate dll export functions?

27,420

Solution 1

dumpbin /exports is pretty much what you want, but that's a developer tool, not a Win32 API.

LoadLibraryEx with DONT_RESOLVE_DLL_REFERENCES is heavily cautioned against, but happens to be useful for this particular case – it does the heavy lifting of mapping the DLL into memory (but you don't actually need or want to use anything from the library), which makes it trivial for you to read the header: the module handle returned by LoadLibraryEx points right at it.

#include <winnt.h>
HMODULE lib = LoadLibraryEx("library.dll", NULL, DONT_RESOLVE_DLL_REFERENCES);
assert(((PIMAGE_DOS_HEADER)lib)->e_magic == IMAGE_DOS_SIGNATURE);
PIMAGE_NT_HEADERS header = (PIMAGE_NT_HEADERS)((BYTE *)lib + ((PIMAGE_DOS_HEADER)lib)->e_lfanew);
assert(header->Signature == IMAGE_NT_SIGNATURE);
assert(header->OptionalHeader.NumberOfRvaAndSizes > 0);
PIMAGE_EXPORT_DIRECTORY exports = (PIMAGE_EXPORT_DIRECTORY)((BYTE *)lib + header->
    OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
assert(exports->AddressOfNames != 0);
BYTE** names = (BYTE**)((int)lib + exports->AddressOfNames);
for (int i = 0; i < exports->NumberOfNames; i++)
    printf("Export: %s\n", (BYTE *)lib + (int)names[i]);

Totally untested, but I think it's more or less correct. (Famous last words.)

Solution 2

Go over to Microsoft research and grab the Detours Library. One of its examples does exactly what you are asking. The whole library basically makes detouring/rerouting win32 function calls extremely easy. Its pretty cool stuff.

Detours

Edit: Also note that if you just want to look at the export table, you can (at least in visual studios) set your project properties to print out the export/import tables. I can't remember the exact option but should be easy to google.

**Edit2:**The option is Project Properties->Linker->Debugging->Generate MapFile ->Yes(/MAP)

Solution 3

While ephemient is correct that LoadLibraryEx with DONT_RESOLVE_DLL_REFERENCES can simplify this task a great deal, you can make it even simpler than he shows. Instead of finding and enumerating the DLL's export directory yourself, you can use SymEnumerateSymbols to list the symbols for you.

Although only marginally simpler than his code (without the asserts, his is only half a dozen lines of code) this at least theoretically gives a little extra flexibility in case Microsoft should someday decide to change the executable format a bit, and/or change exactly what the HMODULE points at, so his no longer works (since most of these details aren't officially documented anyway).

Solution 4

If you don't want to go to the trouble of writing your own code and would rather use a DLL that already exists for this purpose, I recommend PE File Format DLL. Comes with source code so that you can modify if you wish. No GPL to worry about.

Also available is a GUI application that shows how to use the DLL.

Share:
27,420
user15071
Author by

user15071

Updated on March 04, 2021

Comments

  • user15071
    user15071 about 3 years

    I found similar questions but no answer to what I am looking for. So here goes:

    For a native Win32 dll, is there a Win32 API to enumerate its export function names?

  • Peter Hansen
    Peter Hansen about 14 years
    Worked well enough that my quick port to Python (with ctypes) works fine. Thanks!
  • Janusz Lenar
    Janusz Lenar over 11 years
    It is essential to note that calling the functions after loading with the DONT_RESOLVE_DLL_REFERENCES flag might blow shit up, because no DllMain is called for the loaded module.
  • masterxilo
    masterxilo over 8 years
    Why not just memory-map the file yourself instead of the DONT_RESOLVE_DLL_REFERENCES? Might be faster even.
  • IInspectable
    IInspectable about 8 years
    @masterxilo: LoadLibrary[Ex] do memory-map the binary into the address space. Why complicate things?
  • Chad Schouggins
    Chad Schouggins about 7 years
    It seems DONT_RESOLVE_DLL_REFERENCES is required as the virtual address in the exports dictionary isn't valid when just memory mapped. LoadLibrary apparently does some necessary transformation. At least I'm seeing this on my Win10 x64.
  • Simon Mourier
    Simon Mourier over 2 years
    The problem with this is when the file is not ok (like bad format, etc.), it will display an error message box that must be clicked. Also devblogs.microsoft.com/oldnewthing/20050214-00/?p=36463