Compilation de la bibliothèque C ++ externe pour une utilisation avec le projet iOS
Je suis complètement nouveau à l'aide de bibliothèques C++, afin d'apprécier ce pourrait être un peu précis pour mon cas (laissez-moi savoir et je peux fournir plus de détails).
J'ai un externe de la bibliothèque C++ que je suis en train de l'utiliser avec un projet iOS. La bibliothèque suit un configure, make, make build modèle à sortie une .un fichier de bibliothèque. Lorsque j'essaie d'ajouter ce fichier de bibliothèque de Xcode, j'obtiens l'erreur suivante:
ignorant fichier
/Utilisateurs/Développeurs/iOS/TestProj/libpresage.un, dossier était
construit pour les archives, qui n'est pas l'architecture (i386):/Utilisateurs/Développeurs/iOS/TestProj/libpresage.un
Basé sur cette questionj'ai essayé de tourner Construire Active de l'Architecture, Seule, et j'obtiens la même erreur. Ce qui me fait soupçonner que j'ai compilé la bibliothèque de la mauvaise architecture.
L'exécution de lipo -info sur le .un fichier donne:
fichier d'entrée libpresage.a n'est pas un gros fichier Non gras du fichier: libpresage.un
est l'architecture: x86_64
Étant donné que ce n'est pas armv7s, armv7, ou arm64, j'essaie de le compiler la bibliothèque C++ de nouveau avec les paramètres suivants:
1) Essayer
./configure CC="gcc -arch armv7s" \
CXX="g++ -arch armv7s" \
CPP="gcc -E" CXXCPP="g++ -E"
Erreur à la compilation, j'obtiens:
ld: library not found for -lcrt1.3.1.o
clang: error: linker command failed with exit code 1 (use -v to see invocation)
2) Essayer
./configure CC="gcc -arch arm64" \
CXX="g++ -arch arm64" \
CPP="gcc -E" CXXCPP="g++ -E"
Erreur à la compilation, j'obtiens:
ld: warning: ld: avertissement: le non-respect de fichier
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.10.sdk/usr/lib/libSystem.dylib,
manque architecture arm64 dans le fichier
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.10.sdk/usr/lib/libSystem.dylib
(2 tranches)en ignorant fichier
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.10.sdk/usr/lib/libstdc++.dylib,
manque architecture arm64 dans le fichier
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.10.sdk/usr/lib/libstdc++.dylib
(2 tranches)ld: dynamique principaux exécutables doivent lien avec libSystem.dylib pour
l'architecture arm64 clang: erreur: échec de la commande de l'éditeur de liens avec le code de sortie
1 (v pour voir invocation)
Il est évident que je suis absent?
EDIT:
Merci pour les réponses, j'ai donc réussi à obtenir de la bibliothèque dans Xcode comme une cible de génération personnalisée, en pointant le "faire" commande pour les bibliothèques MakeFile. Cette construction d'amende.
Mon étapes à partir d'ici:
- Ajouter une dépendance de mon Objectif C de l'application iOS de la cible de la cible de génération personnalisée.
- Référence à la bibliothèque et faire un Objectif wrapper C++.
- Cela semble bien jusqu'à ce que j'ai besoin d'appeler le externe de la bibliothèque C++, puis je reçois le message d'erreur lors de la compilation:
Les symboles non définis pour l'architecture armv7:
"Présage::Presage(PresageCallback*)", référencé à partir de:
-[PresageBridge init] dans PresageBridge.o
"Présage::~Presage()", référencé à partir de:
-[PresageBridge init] dans PresageBridge.o
ld: symbole(s) ne se trouvent pas pour l'architecture armv7
clang: erreur: échec de la commande de l'éditeur de liens avec le code de sortie 1 (l'option-v pour voir invocation)
- Mon objectif wrapper C++ (liens externes de la bibliothèque C++ de l'en-tête présage.h):
#import "PresageBridge.h" #include "presage.h" @implementation PresageBridge - (instancetype)init { if(self = [super init]) { Presage hello(&callback); } return self; }
- Basé sur le code ci-dessus, il ne semble pas comme je suis absent de l'en-tête, et ce qui est intéressant, c'est que j'ai aussi essayé de créer une instance d'autres classes dans la bibliothèque externe et ils semblent être au travail, ce qui suggère que Xcode ne pouvez pas lier le présage.h correctement pour une raison quelconque.
source d'informationauteur HHHH
Vous devez vous connecter pour publier un commentaire.
J'ai donc utilisé de nombreux une 3ème partie de la bibliothèque C++ dans mon iOS projets. Il existe différentes stratégies que les gens utilisent pour cela. Comme certains l'ont déjà cité, vous pouvez inclure le code dans le projet directement, construire la lib statique avec Xcode, ou construire la ligne de commande. Dans le cas de la croix-plate-forme de C++ libs qui utilisent la GNU configurer et construire le système, je préfère la ligne de commande. Vous avez seulement besoin de construire une fois et vous n'avez qu'à revenir si vous avez besoin de mettre à jour la version ou ajouter une nouvelle architecture de la tranche.
La généralisation de l'approche que vous voulez est:
Figure le droit de configurer les arguments à utiliser pour la construction de chaque tranche. Généralement, vous avez seulement besoin de se concentrer sur l'obtention de l'un des bras ainsi que i386 de travail. Le reste est facile, vous avez fait cela. Dans certains cas, vous devez modifier le fichier de configuration pour ajouter de l'hôte ou de faire d'autres ajustements.
Une fois que vous pouvez construire toutes les tranches, vous souhaitez exécuter lipo pour construire un gros binaire.
La meilleure façon de régler ce problème est de créer un script de compilation qui fera tout le travail pour vous. De cette façon, il est plus facile de refaire. Plus important encore, vous pouvez réutiliser le script ou permuter pour construire d'autres libs externes.
Il existe de nombreuses façons que vous pouvez construire le script. En voici une. Il m'arrive d'avoir plusieurs variantes de ce type de script. Ce script a été utilisé pour construire cURL. Il est plus ou moins travaillé pour présager de très peu de mod (ie. changement curl présager). Remarque je n'ai pas le tester dans Xcode (ie. le liant et en l'exécutant). Je l'ai fait savoir que je devais désactiver sqlite, sinon, il construit des éléments d'outils qui ne construit pas de droit. Si vous en avez besoin, vous pouvez comprendre cette partie.
Il y a beaucoup de manières que vous pourriez le rendre plus lisse. Par exemple l'utilisation d'un tableau pour stocker toutes les architectures. C'est juste de la force brute.
Les points clés d'un script sont:
Noter qu'il devrait travailler hors de la boîte, cependant, YMMV. Soyez prêt à le corriger si nécessaire. Par exemple, je n'ai pas confirmé le type d'hôte, mais en général, c'est ce que j'ai toujours utilisé. Vous voulez mettre ceci à l'annuaire pour les presage (même répertoire où configurer). Quand c'est fait, toutes les architectures sont dans le répertoire de sortie. L'universel lib est le présage d'annuaire.
Rappelez-vous aussi qu'il est de votre responsabilité de bien lien dans l'universel lib ainsi que les fichiers d'en-tête de la recherche de chemin d'accès défini correctement.
Considérant que vous êtes de nouveau avec les bibliothèques C++, je suppose que vous aurez besoin de faire un peu plus de recherche.
Cependant, je vais tenter d'esquisser quelques étapes choses que vous devez prendre en considération :
Il y a de multiples façons d'aborder ces questions .
Pour le premier, je suggère d'inclure dans votre espace de travail à la bibliothèque statique, et ajoutez-la à la dépendance à votre cible de génération . Pour cela, vous devez comprendre XCode construit.
Je devine que vous êtes effectivement en essayant de faire une application de téléphone, donc pour la 3ème option, vous devez configurer votre g++ construire à le regarder dans les iPhoneSDK de XCode lors de la liaison de bras cibles (s'occuper de l'iPhoneOS.la plate-forme) pour cela.
De faire un bras de construire ne fonctionne que sur iphone . Si vous voulez qu'il fonctionne sur simulateur , vous devez lier votre bibliothèque statique pour les bibliothèques à l'intérieur de la iPhoneSimulator.la plate-forme.
Si vous voulez que votre bibliothèque statique pour travailler à la fois pour iphone et iPhone simulator, vous aurez besoin de faire un gros lib (en gros une bibliothèque contenant des symboles pour les deux plates-formes)
Si vous êtes absent de ces plates-formes, vous pouvez les télécharger à partir de XCode (mais je crois qu'ils sont là)
Comme vous pouvez le voir, les choses vont devenir de plus en plus complexes le long de la voie, donc je vous recommande fortement d'utiliser XCode pour la compilation de la bibliothèque statique (c'est encore faisable avec g++ tu).
Je crois que les concepts suivants vous serait utile pour la recherche sur :
Espère que cela aide :).
Voici ce qui a fonctionné pour moi dans Xcode 9 pour les appareils iOS (iPhone X):
1) Compiler dylib avec ces drapeaux défini comme suit:
a) le Répertoire "Installation":
@executable_path/Cadres
b) "Runpath Chemin de Recherche":
@executable_path/Cadres
Voir l'image ci-dessous:
dylib paramètres dans Xcode 9
2) Dans le projet Xcode où la dylib est utilisé/lien:
a) "Runpath Chemin de Recherche":
@executable_path/Cadres
b) Dans la Phase de construction->Intégrer les Bibliothèques" assurez-vous que vous sélectionnez "Destination" comme "Exécutables" et Subpath comme des "Cadres", "Code de signer sur la copie" coché:
Réglage de la le lien de l'application iOS
Cette méthode est testé et utilisé avec Xcode 9.2 et iPhone X.
David
C++ Fonctionne sur iOS, vous pouvez simplement l'ajouter dans votre projet. Ou si vous voulez vraiment avoir votre bibliothèque dynamique, vous pouvez le compiler avec Xcode et spécifier votre architecture cible.
Définir votre architecture par défaut essayez les solutions suivantes.
1. Dans les Phases de construction->Lien Binaire Avec les Bibliothèques ajouter libz.dylib et libxml2.dylib bibliothèques à votre projet.
2. Dans BuildSettings->Chemins de Recherche de Toujours Rechercher les Chemins de l'Utilisateur à Oui, et dans le Cadre des Chemins de Recherche ajouter le chemin d'accès correct de votre cadre. Utiliser le terminal pour obtenir le droit chemin d'accès de votre cadre.
3. Essayez de régler vos "sources du Compilateur" C++ ou de l'utilisation de frapper et d'essai et de vérifier avec toutes les options. Complier Source Comme l'est aussi en vertu de BuildSettings. Utilisez cmd+f pour rechercher.
De les essayer et laissez-moi savoir, aussi me dire sur le cadre ou le sdk que vous essayez de les utiliser dans votre projet.
Le script par Mobile Ben est grand, en dehors de la ligne de code en dur une bibliothèque de nom de fichier dans le script. Ce qui suit est un remplacement pour la dernière lipo de commande et de manière dynamique utilise des lipo fusionne chaque fichier de la bibliothèque créée après la compilation.
Changer de Mobile Ben ligne:
:
Remarque: je n'ai pas envie de modifier Mobiles Ben la réponse avec le nouveau code, la fonctionnalité, et l'ajout de cette comme un commentaire perdu de mise en forme.