2009-12-19 13 views
7

Ich unterhalte eine small application, die einige Plugin-ähnliche Funktionalität hat, die durch Laufzeit-geladene dynamische Module implementiert wird.Zugriff auf Hauptprogramm globale Variablen von einer dlopen() ed dynamische Bibliothek in C unter OS X

Da es sich um eine Gtk + -App handelt, verwende ich gmodul, aber die Frage bezieht sich auch auf das dynamische Laden der dlfcn.h/dlopen() - Bibliothek.

Mein Hauptprogramm hat eine einzelne globale Strukturvariable, die einige globale Informationen enthält. Ich möchte, dass diese Information für Funktionen verfügbar ist, die in den dynamisch geladenen Plugins definiert sind.

Unter Linux konnte ich direkt auf diese globale Variable verweisen - das funktioniert gut, und ich denke, dass gcc oder der Linker kümmern sich um den Export der globalen Variablen aus dem Hauptprogramm in dynamische Bibliotheken.

Problem ist, dass dies unter Mac OS X nicht funktioniert. Gibt es eine Möglichkeit, dies unter OS X zu tun?

Wenn nicht, gibt es eine "Best Practice" Möglichkeit, globale Informationen dynamisch geladenen Bibliotheken zugänglich zu machen?

+0

BTW hier ist ein Beispiel Code, der das Problem vereinfacht: http://pastie.org/749794 – shevron

Antwort

10

Setzen Sie die globale in main.c und erklären sie extern in das Objekt geteilt, und versuchen Sie dies:

MACOSX_DEPLOYMENT_TARGET=10.3 ld -dylib -undefined dynamic_lookup -o multiply.so multiply.o 

oder

MACOSX_DEPLOYMENT_TARGET=10.3 libtool -dynamic -undefined dynamic_lookup -o multiply.so multiply.o 

Es ist für mich auf Mac OS X 10.4 arbeitete

+0

Danke, das funktioniert! Ich habe die TAGET-Umgebung allerdings nicht benutzt, ich vermute, das ist weniger verwandt. Jetzt, um zu sehen, wie man das in meine Makefiles integriert! – shevron

+0

Es funktioniert auch Verzeichnis von gcc: gcc -Wall -g-fPIC -c multiplizieren.c gcc-Shared-Wl, -undefined, dynamic_lookup -o multiplizieren.so multiplizieren.o – shevron

3

Da Sie

int global; 

im multiply.h Header deklarieren, die DLL und Hauptprogramm haben beide ihre eigene Kopie davon. Stattdessen erklären die globale in main.c

int global; 

und in multiply.c als extern deklarieren:

extern int global; 

Nun, wenn Sie main.cpp mit der Option -rdynamic Option verknüpfen, dann die Symbole der ausführbaren Datei wird in die DLL exportiert.

Ich habe dies unter Linux getestet und es hat funktioniert, aber ich habe Angst, ich habe keinen Zugriff auf MacOS zu testen. Da Ihr ssample-Code unter Linux nicht funktioniert hat, war dies wahrscheinlich das Problem.

+0

AFAIK-Rdynamic wird nicht unter OS X. In jedem Fall habe ich einen Fehler über "_global" undefiniert, wenn Sie versuchen, zu verknüpfen multiply.o – shevron

Verwandte Themen