2016-05-10 9 views
2

Szenario:-rdynamic nur für ausgewählte Symbole?

Ausführbare Datei lädt gemeinsames Objekt zur Laufzeit über dlopen.

Das gemeinsame Objekt verweist auf ein Symbol (eine Funktion), das tatsächlich in die Hauptdatei kompiliert wird.

Dies funktioniert gut, wenn ich -dynamic gcc beim Verknüpfen der ausführbaren Datei hinzufügen.

-rdynamic exportiert alle nicht statischen Symbole der ausführbaren Datei. Mein geteiltes Objekt benötigt nur einige wenige.

Frage: Gibt es eine Möglichkeit, den Effekt von -rdynamic zu erreichen, aber die wenigen Auswahlsymbole, von denen ich weiß, dass sie von meinem gemeinsamen Objekt benötigt werden, eingeschränkt sind?

Edit:

Mindestens zwei Menschen falsch verstanden die Frage, also versuche ich zu klären:

Diese Frage bezieht sich auf ein Symbol aus dem Hauptprogramm exportieren.

Diese Frage ist nicht über das Exportieren eines Symbols aus einer dynamischen Bibliothek.

ist hier ein minimales Beispiel:

func.h, die gemeinsame Headerdatei

#include <stdio.h> 
void func(void); 

main.c, die wichtigsten ausführbaren Code:

#include <dlfcn.h> 
#include "func.h" 

// this function is later called by plugin 
void func(void) { 
    printf("func\n"); 
} 

int main() { 
    void * plugin_lib = dlopen("./plugin.so", RTLD_NOW); 
    printf("dlopen -> %p, error: %s\n", plugin_lib, dlerror()); 

    // find and call function "plugin" in plugin.so 
    void (*p)(void); // declares p as pointer to function 
    p = dlsym(plugin_lib, "plugin"); 
    p(); 

    return 0; 
} 

plugin.c, code für das zur Laufzeit geladene Plugin:

#include "func.h" 

void plugin() 
{ 
    printf("plugin\n"); 
    func(); 
} 

Wenn ich kompilieren mit

$ gcc -o main main.c -ldl 
$ gcc -shared -fPIC -o plugin.so plugin.c 

Dann können plugin.so nicht geladen werden, da sie das Symbol func verweist, die nicht gelöst werden können:

$ ./main 
dlopen -> (nil), error: ./plugin.so: undefined symbol: func 
Segmentation fault (core dumped) 

ich das Hauptprogramm überzeugen können alle exportieren ihre globale Symbole mit der Option -rdynamic Kompilieren:

$ gcc -rdynamic -o main main.c -ldl 
$ ./main 
dlopen -> 0x75e030, error: (null) 
plugin 
func 

Aber das füllt die dynamische Symboltabelle unnötig mit allen Symbolen.

(Diese dynamische Symboltabelle kann mit nm -D main überprüft werden.)

Die Frage ist, wie kann ich nur „Func“ auf die dynamische Symboltabelle der Haupt ausführbaren Datei, und nicht alles hinzuzufügen.

+0

Mögliches Duplikat von [Explizite Exportieren von Funktionen der gemeinsam genutzten Bibliothek in Linux] (http://StackOverflow.com/questions/2164827/explicitly-exporting-shared-library-functions-in-linux) – greydet

+0

Mögliches Duplikat von [wie anrufen Funktion in der ausführbaren Datei von meiner Bibliothek?] (http://stackoverflow.com/questions/6292473/how-to-call-function-in-executable-from-my-library) – ninjalj

+0

@ninjalj Nice find! Diese Frage selbst ist nicht meine Frage. Aber es hat eine Antwort http://stackoverflow.com/posts/6298434/revisions, die auch meine Frage beantwortet. –

Antwort

0

Sie könnten es mit dem Sichtbarkeitsattribut von GCC tun.

Deklarieren Sie die zu exportierende Funktion mit __attribute__ ((visibility ("default"))) Flag. Kompilieren Sie dann Ihre gesamte Bibliothek, indem Sie das Argument -fvisibility=hidden an GCC übergeben.

Eine vollständige Erläuterung hierzu finden Sie in der folgenden Datei GCC documentation page.

+0

Danke, aber Nein. Meine Frage bezieht sich auf den Export von Symbolen aus der Hauptdatei, nicht aus einer Bibliothek. –

1

Leider ist es schwieriger, dies für ausführbare Dateien zu erreichen. Sie müssen eine Liste der Symbole erstellen, die Sie exportieren möchten, und dann -Wl,--dynamic-list=symfile.txt zu LDFLAGS hinzufügen.

Here's example wie es in Clang gemacht wird (und here ist das Skript, das sie verwenden, um die Symboldatei zu erzeugen).

+0

Ja, -Wl, - dynamic-list = ist der Weg, dies zu tun. Unter https://stackoverflow.com/posts/6298434/revisions finden Sie eine Antwort, die eine Beispielsymboldatei enthält. –