Einbinden von dynamischen libraries unter Linux



  • Hallo.

    Ich arbeite mit C++ gewöhnlich unter Windows mit DevCPP, muss meinen Code aber gelegentlich auf Linux clustern laufen lassen. Bis jetzt hat das auch prima funktioniert, allerdings habe ich jetzt folgendes Problem:

    Ich benutze unter anderem die GSL und TIFF Bibliotheken. Auf den Linuxrechnern, auf denen ich bisher gearbeitet habe, waren jeweils statische Bilbiotheken vorhanden (zB /usr/lib/libgsl.a), die ich problemlos per

    c++ source.cpp -o executable -lgsl (etc.)eingebunden hab.

    Auf dem anderen Rechnersystem sind jetzt aber nur shared object libraries (zB /usr/lib64/libgsl.so.0.8.0 und /usr/lib/libtiff.so.3.8.2) vorhanden, und der Compiler meckert mir die Bibliotheken als fehlend an (alle verwendeten Methoden und Typen werden nicht erkannt, so als hätte ich die Bibliothek nicht included). Habe jetzt eine ganze Weile über Google versucht, den Fehler zu finden, bisher aber erfolglos. Meine Recherche scheint aber anzudeuten, daß die compiler-Kommandozeile genauso auch für .so Bibliotheken funktionieren sollte.

    Mache ich irgendwo noch einen grundlegenden Fehler?



  • Sieht so aus, als hättest du ein Problem mit 32bit/64bit.

    Vielleicht hilft ein -m64 als Compiler-Flag oder ein -L/usr/lib64

    Ansonsten solltest du darauf achten, dass du links hast, die lib*so auf die lib*.so.VERSION linken, da der GCC bzw. der Linker nur nach lib*.so bzw. lib*.a sucht.



  • Hast Du die development-Pakete installiert?

    Wenn Deine Fehlerbeschreibung stimmt und der Compiler meckert, dann kann das nicht an den Bibliotheken liegen. Oder meckert doch der Linker? Poste doch mal eine Fehlermeldung.

    Prinzipiell ist das kein Unterschied bei Compilieren und Linken, ob Du statische oder dynamische Bibliotheken verwendest. Der Linker sucht zunächst nach Dateien mit der Endung .so und dann nach .a. Findet er .so-Dateien, werden diese verwendet und somit dynamisch gebunden. Hast Du keine dev-Pakete installiert fehlen die Header und auch die .so-Dateien. Du hast dann in der Regel nur Dateien mit .so-<versionsnummer>. Mit denen kann der Linker nichts anfangen.

    Tntnet



  • Vielen Dank für die Antworten!

    Also, die Fehlermeldung ist die folgendende (bleibt gleich mit und ohne -m64 und -L/usr/lib64):

    tcsh% g++ generalDriver.cpp -o gd -lgsl -lgslcblas -ltiff -m64
    In file included from generalDriver.cpp:13:
    eigeneUtils.cpp:12:25: error: gsl\gsl_rng.h: No such file or directory
    eigeneUtils.cpp:13:29: error: gsl\gsl_randist.h: No such file or directory
    eigeneUtils.cpp:14:20: error: tiffio.h: No such file or directory
    In file included from generalDriver.cpp:28:
    newFHN.cpp:13:27: error: gsl/gsl_errno.h: No such file or directory
    newFHN.cpp:14:28: error: gsl/gsl_matrix.h: No such file or directory
    newFHN.cpp:15:27: error: gsl/gsl_odeiv.h: No such file or directory
    newFHN.cpp:17:25: error: gsl/gsl_rng.h: No such file or directory
    newFHN.cpp:18:29: error: gsl/gsl_randist.h: No such file or directory

    [an dieser Stelle sollte ich anmerken, der #include ... code hat auf anderen Linux Systemen funktioniert]

    eigeneUtils.cpp:31: error: expected constructor, destructor, or type conversion before '' token
    eigeneUtils.cpp: In function 'void startRNG(const unsigned int&)':
    eigeneUtils.cpp:36: error: expected initializer before '
    ' token
    eigeneUtils.cpp:37: error: 'gsl_rng_env_setup' was not declared in this scope
    eigeneUtils.cpp:38: error: 'eu_T' was not declared in this scope
    [...usw...]

    Ich glaube das primäre Problem ist nicht das lib64 Verzeichnis, weil die TIFF befindet sich ja im lib Verzeichnis und für die bekomme ich auch Fehler.

    im /usr/lib Verzeichnis finden sich folgende Dateien für die TIFF:
    libtiff.so.3 (link)
    libtiff.so.3.8.2

    im /usr/lib64 Verzeichnis für die GSL:
    libgsl.so.0 (link)
    libgsl.so.0.8.0
    libgslcblas.so.0 (link)
    libgslcblas.so.0.0.0

    Die Links scheinen alle die Gestalt .so.(erste Ziffer der Versionsnummer) zu haben. Wenn ich so durch das /usr/lib Verzeichnis schaue, finde ich für andere libs oft folgende Dateien:
    libX.so (link)
    libX.so.Y (link)
    libX.so.Y.Z (großes file)

    Es gibt aber auch viele, bei denen die .so fehlt, so wie bei den libs die ich benutzen möchte.

    Hilft das jemandem dabei, mir dabei zu helfen, mir selbst zu helfen? Muss ich den SysAdmin bitten, weitere packages zu installieren (developer files)? Kann ich den ganzen Kram anders einbinden (würde ein makefile helfen)?

    Gruß,

    Daniel



  • Das Problem hat überhaupt nichts mit den Bibliotheken zu tun. Der Compiler findet die Header nicht. Wie schon angedeutet fehlen die Entwicklungspakete. Bibliotheken sind unter Linux normalerweise unterteil in Laufzeitpakete und Entwicklungspakete, die getrennt installiert werden können. So gibt es beispielsweise unter ubuntu die Pakete libtiff4 und libtiff4-dev. Zum ausführen der Programme benötigst Du libtiff4. Willst Du Programme übersetzen, benötigst Du zusätzlich libtiff4-dev. Das enthält dann unter anderen die Header-Dateien.

    Ach ja - da fällt mir noch was auf: der sucht nach einer Datei "gsl\gsl_rng.h". Das soll natürlich "gsl/gsl_rng.h" heissen.

    Tntnet



  • Ah, das klärt einiges (das mit den dev Paketen).

    Ok, dann muss ich glaub ich den Admin mal treten, dass er die noch installiert, weil er meinte man muss die Programm unbedingt auf dem cluster kompilieren.

    Guter Punkt auch mit den / statt \, muss ich mal ändern. Unter Windows funktioniert glaub ich eh beides.

    Danke für die Antworten!


Anmelden zum Antworten