17 votes

Comment distribuer un Mac OS X avec des bibliothèques dépendantes ?

J'ai un programme (plus précisément mon entrée pour le Défi de l'application SO DevDays Countdown ) qui s'appuie sur plusieurs bibliothèques dynamiques, à savoir libSDL, libSDL_ttf et d'autres. Ces bibliothèques sont installées sous /opt/local/lib via MacPorts, et beaucoup de gens ne les auront pas installés (et certains les auront peut-être installés, mais pas à cet endroit).

Comment puis-je distribuer mon programme de manière à ce que les personnes qui n'ont pas installé ces bibliothèques puissent l'exécuter sans problème ? Il est évident que je vais devoir distribuer les différentes .dylib mais cela ne suffit pas. Le chargeur dynamique recherche toujours les bibliothèques installées aux endroits où je les ai installées. Existe-t-il un moyen d'indiquer au chargeur dynamique de chercher dans le répertoire courant de l'exécutable, comme le fait Windows avec les DLL ? Il ne devrait pas être nécessaire de modifier les variables d'environnement (par ex. DYLD_LIBRARY_PATH ), car je veux que cela fonctionne dès le départ.

13voto

nall Points 10996

L'approche de base consiste à les intégrer dans le paquet .app. Vous modifierez alors l'emplacement où l'éditeur de liens recherche les bibliothèques partagées pour les inclure.

Les étapes sont les suivantes :

  1. Créez une nouvelle phase de construction de fichiers de copie vers votre cible qui copie ces fichiers dans le répertoire Frameworks du bundle .app.

  2. Modifier le paramètre de configuration de la construction "Runpath Search Paths" pour inclure @executable_path/../Frameworks

Si vous compilez votre exécutable avec ces changements et que vous regardez ensuite, vous devriez trouver que les dylibs existent dans le répertoire Foo.app/Contents/Framework et de lancer otool -L Foo.app/Contents/MacOS/Foo devrait produire une entrée préfixée par @rpath pour ces dylibs.

A partir de là Poste Cocoabuilder :

En général, @loader_path est préféré à @executable_path , car il
permet aux cadres intégrés de fonctionner à la fois dans un exécutable et dans un paquet,
plugin, ou sous-cadre. Le seul inconvénient est que @loader_path
nécessite la version 10.4 ou une version plus récente. Si vous êtes sur 10.5 ou plus récent, @rpath est même
mieux que @loader_path .

7voto

Dietrich Epp Points 72865

Comme vous l'avez mentionné, vous n'utilisez pas Xcode, donc c'est un peu difficile. Voici les options par ordre de préférence :

  1. Passer à Xcode. Utiliser des cadres. Les bibliothèques SDL sont déjà disponibles sous forme de frameworks, et j'ai vu plus d'un jeu commercial avec un libsdl.framework dans l'app bundle.

  2. Utiliser des frameworks, mais garder ses Makefiles. Téléchargez les versions "framework" de vos bibliothèques SDL (ou compilez-les vous-même), et liez-les avec l'option -framework linker. Distribuez les frameworks avec votre application ou non, et dites à vos utilisateurs de les placer dans ~/Library/Frameworks ou dans /Library/Frameworks. Je ne m'embarrasserais pas d'un installateur pour cela.

  3. Lien statique avec SDL. Dans le Makefile, vous devrez lister le chemin des bibliothèques statiques plutôt que d'utiliser le drapeau -l, par exemple en lançant "ld blah blah /opt/local/lib/libsdl.a". À ma connaissance, il n'existe aucun moyen d'indiquer à -l de préférer les bibliothèques statiques aux bibliothèques partagées, et croyez-moi, j'ai cherché.

3voto

wildwobby Points 71

Lier statiquement les bibliothèques.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X