Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Get functions names in a shared library programmatically

Can I get list of all functions names from a shared library (Linux only) programmatically when I am using dl_open()?

I want something like this:

std::vector<std::string> list_all_functions(void *dl) { 
   //... what can I do here?
}

int main() {
    void * dl = dl_open("./mylib.so", RTLD_NOW);
    auto functions = list_all_functions(dl);
    //...
    dl_close(dl);
    return 0;
}

Example library (mylib.so)

Header (.h):

extern "C" {
    int sum (int a, int b);
}

Source (.c):

int sum (int a, int b) { return a + b; }

Dirty hack that I know: use nm or objdump utility

like image 479
Alex Bar Avatar asked Aug 12 '14 17:08

Alex Bar


1 Answers

There is no libc function to do that. However, you can write one yourself (or copy/paste the code from a tool like readelf).

On Linux, dlopen() returns the address of a link_map structure, which has a member named l_addr that points to the base address of the loaded shared object (assuming your system doesn't randomize shared library placement, and that your library has not been prelinked).

On Linux, a way to find the base address (the address of Elf*_Ehdr) is to use dl_iterate_phdr() after dlopen()ing the library.

Having the ELF header, you should be able to iterate over a list of exported symbols (the dynamic symbol table), by first locating the Elf*_Phdr of type PT_DYNAMIC, and then locating DT_SYMTAB, DT_STRTAB entries, and iterating over all symbols in the dynamic symbol table. Use /usr/include/elf.h to guide you.

Additionally, you could use libelf, that I don't know very well personally.

However, note that you'll get a list of defined functions, but you'll have no idea how to call them.

like image 177
Colin Pitrat Avatar answered Oct 03 '22 20:10

Colin Pitrat