Wie funktioniert es intern?
this answer Wie erläutert, in GLIBC der erste Parameter tatsächlich ein Zeiger auf struct link_map
ist, der genug Informationen enthält, die dynamische Symboltabelle der gemeinsam benutzten Bibliothek zu lokalisieren. Sobald die Symboltabelle und DT_HASH
oder DT_GNU_HASH
lokalisiert sind, verwendet dlsym
die eine oder andere Hash-Tabelle, um den angegebenen Symbolnamen zu finden.
Ist es möglich, eigene, einfache Implementierung von dlsym() zu schreiben?
Ja. Wenn Ihnen die Suchgeschwindigkeit nicht wichtig ist, können Sie einfach die dynamische Symboltabelle linear durchsuchen. Der Code, um dies zu tun ist ziemlich einfach, vor allem, wenn die gemeinsame Bibliothek (optional) Abschnitt Kopfzeile hat: alles, was Sie tun müssen, ist Ort der .dynsym
und .dynstr
Abschnitte im Speicher finden, und dann (vorausgesetzt, Sie suchen nach Symbol
)
const char *strtab = ... /* locate .dynstr */
const ElfW(Sym) *sym = ... /* locate .dynsym */
for (; sym < end_of_dynsym; ++sym) {
if (strcmp(strtab + sym->st_name, "foo") == 0) {
/* found it */
return load_address + sym->st_value;
}
}
/* symbol not found */
return NULL;
Wenn Sie über Lookup-Geschwindigkeit ist egal (dlsym
sicherlich der Fall ist), müssen Sie .hash
oder .gnu_hash
, dekodieren, die etwas komplizierter ist. Sie könnten here starten.