簡體   English   中英

返回共享庫符號表

[英]Returning a shared library symbol table

例如:

void* sdl_library = dlopen("libSDL.so", RTLD_LAZY);
void* initializer = dlsym(sdl_library,"SDL_Init");

假設沒有錯誤,初始化程序將指向共享庫 libSDK.so 中的函數 SD_Init。

然而,這需要知道符號“SDL_Init”存在。

是否有可能查詢一個庫的所有符號? 例如,在這種情況下,它將返回 SDL_Init、函數指針和 libSDL.so 導出的任何其他符號。

沒有 libc 函數可以做到這一點。 但是,您可以自己編寫一個(盡管代碼有些涉及)。

在 Linux 上, dlopen()實際上返回一個link_map結構的地址,該結構有一個名為l_addr的成員,指向加載的共享對象的基地址(假設您的系統沒有隨機化共享庫的位置,並且您的庫具有未預鏈接)。

在 Linux 上,找到基地址( Elf*_Ehdr的地址)的Elf*_Ehdr是在dlopen()庫之后使用dl_iterate_phdr()

有了 ELF 標頭,您應該能夠遍歷導出的符號列表(動態符號表),首先定位Elf*_Phdr類型的Elf*_Phdr PT_DYNAMIC ,然后定位DT_SYMTABDT_STRTAB條目,並迭代所有符號動態符號表。 使用/usr/include/elf.h來指導您。

此外,您可以使用libelf ,但我無法指導您,因為我以前沒有使用它的經驗。

最后請注意,這個練習有點徒勞:您將獲得一個已定義函數的列表,但您不知道如何調用它們(它們期望什么參數),那么有什么意義呢?

我認為沒有為此發布的 API。 您可以使用 binutils 中的 nm 工具或檢查其源代碼: http : //sourceware.org/cgi-bin/cvsweb.cgi/src/binutils/? cvsroot=src

http://sourceware.org/cgi-bin/cvsweb.cgi/src/binutils/nm.c?rev=1.63&content-type=text/x-cvsweb-markup&cvsroot=src

(顯然假設精靈)

Boost.DLL通過library_info::symbols函數提供此功能。 改編自有關查詢符號庫的教程:

// Class `library_info` can extract information from a library
boost::dll::library_info inf(libpath);

// Getting exported symbols
std::vector<std::string> exports = inf.symbols();

// Printing symbols
for (std::size_t j = 0; j < exports.size(); ++j) {
    std::cout << exports[j] << std::endl;
}

請注意,這僅適用於nm列出的沒有--dynamic標志的符號,即.symtab部分中的.symtab 似乎有些庫不導出該部分中的任何符號。 在這種情況下,我已經打開了一個功能請求以支持回.dynsym部分。

void *dlsym(void *restrict handle, const char *restrict name);

返回值

如果handle不引用由dlopen()打開的有效對象,或者如果在與handle關聯的任何對象中找不到命名符號,則dlsym()應返回 NULL。 應通過dlerror()獲得更詳細的診斷信息。

(來源: http : //www.opengroup.org/onlinepubs/009695399/functions/dlsym.html

換句話說,如果沒有找到符號, dlsym()將返回NULL 不確定這是否是您要找的,但這是我能找到的最簡單的方法。

可以使用 linux nm命令: http : //man.yolinux.com/cgi-bin/man2html? cgi_command= nm

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM