À l'aide de Visual Studio 2010, comment peut-on lier à une DLL générée par Visual Studio 2008
Mes questions sont:
- Est-il possible d'établir un lien de VS2008
généré Dll à l'aide de VS2010? - Si non, pourquoi semble-t-il être
possible de les associer à des bibliothèques statiques
généré par VS2008. - Je vois que VS2010 dispose désormais d'une Plate-forme
Jeu d'outils de l'option. Mais que de laisser
les gens mis à v90 au lieu de v100
même si ils n'ont pas de VS2008
installé? - Même si j'utilise le /Z7 compilateur
commutateur, pourquoi dois-je toujours besoin d'avoir un
.apb pour déboguer Dll.
Les Détails
Je peux utiliser Visual Studio 2010 pour le lien vers mon Leptonica C bibliothèques statiques générés par Visual Studio 2008 sans aucun problème. (Voir la Références section ci-dessous pour plus de détails sur la manière dont je construis Leptonica et un lien vers elle.)
Cependant, lorsque j'essaie de le lien le même programme (leptonlib-1.67\prog\ioformats_reg.c) avec mon VS2008 généré DLL de la version de Leptonica le programme se bloque. Le débogage, je peux voir que le problème est que ioformats_reg.c fait ceci:
fp = fopen(filename, "rb"); /* in ioformats_reg.c */
et, peu après, dans le leptonlib.dll ce qui suit est faite, qui se bloque:
rewind(fp); /* in leptonlib.dll */
Comment faire un lien avec le bon runtime C (CRT) de la bibliothèque dit:
Une bibliothèque réutilisable et l'ensemble de ses
les utilisateurs doivent utiliser la même bibliothèque CRT
types et par conséquent le même compilateur
interrupteur...Si vous choisissez de mélanger les bibliothèques CRT,
rappelez-vous que vous avez deux
des copies de la CRT, séparés et
états distincts, de sorte que vous devez être
attention à ce que vous essayez de faire
sur un CRT-frontière. Il y a beaucoup de
les moyens d'avoir des ennuis avec deux
Des tubes cathodiques. Voici quelques-uns:
- Il y a deux tas distincts. Vous ne pouvez pas allouer (explicitement à nouveau,
malloc, ou-ou implicitement avec
strdup, strstreambuf::str, ou ainsi de suite),
et puis passer le pointeur sur une
CRT-limite d'être libéré.- Vous ne pouvez pas passer d'un FICHIER* ou descripteur de fichier sur un CRT-frontière et
attends le "stdio faible niveau d'e /s" à
travail.- Vous ne pouvez pas définir les paramètres régionaux dans l'un et espérer que les autres locale de l'être ensemble.
À partir de Visual C++ 4.0, le
l'éditeur de liens émet un avertissement (LNK4098)
si, partant, d'un module de tentatives de
combiner plus d'une copie de la CRT
de la bibliothèque. Pour plus d'informations, recherche
le fichier d'Aide pour LNK4098.
Mais je ne pas obtenir tout LNK4098 messages d'erreur de l'VS2010 de l'éditeur de liens.
Leptonica utilise fopen(), rewind(), fclose(), etc. dont la documentation catégorise Flux I/O pas de "bas niveau d'e /s", mais ceux-ci passent autour de FICHIER ptrs. Je suppose que c'est ce que Microsoft veut dire quand ils disent "stdio faible niveau d'e /s".
/MD /MT /LD (Utilisation de la Bibliothèque Run-Time) dit:
Tous les modules passé à une invocation de la
l'éditeur de liens doit avoir été compilé avec le même temps d'exécution
bibliothèque de l'option de compilateur (/MD /MT /LD).
Il n'est pas dire que tous les modules doivent être compilées par la même version du compilateur. Je ne l'utilisation de /MD (ou /MDd) de façon correcte et systématique pour tous mes modules.
Lors de l'utilisation de Dll, il apparaît que la Dll non seulement d'utiliser le même commutateur /MD, mais ils doivent aussi être compilé par VS2010?
Mon cas de test, ce qui semble indiquer que le lien avec les bibliothèques statiques générées par VS2008 fonctionne, mais j'ai peut-être eu de la chance? Pourquoi lier à VS2008 généré bibliothèques statiques de travail, tout en les reliant à un VS2008 généré DLL n'a pas lors de l'utilisation de VS2010?
Est-ce à dire que je dois livrer des Dll distinctes pour une utilisation par VS2008 et VS2010 utilisateurs?
Et que dire de la nouvelle Plate-forme d'Outils option? Peut VS2010 aux utilisateurs de changer que de v900, même si elles n'ont pas de VS2008? Si oui, alors je pourrais juste dire aux gens de changer ce paramètre pour mon Leptonlib-1.67 projet.
Enfin, j'ai utiliser le commutateur /Z7 lors de la création de mes bibliothèques. La documentation à /Z7, /Zi, /ZI (Informations de Débogage Format) états:
/Z7
Produit une .obj fichier contenant plein symbolique
les informations de débogage pour une utilisation avec le débogueur.
Les informations de débogage symbolique inclut les noms
et les types de variables, ainsi que des fonctions et de la ligne
les numéros. Pas de .fichier pdb est produite.Pour les distributeurs de bibliothèques de tiers, il est
un avantage à ne pas en avoir un .fichier pdb. Cependant, l'
.les fichiers obj pour les en-têtes précompilés sont nécessaires
au cours de la phase de liaison, et de débogage. Si ce n'est que
type d'information (et pas de code) dans l' .pch fichiers de l'objet,
vous aurez également à compiler avec
/Yl (Injecter de la PCH de Référence pour le Débogage de la Bibliothèque).
Je ne suis pas à l'aide de tous les en-têtes précompilés. Toutefois, c'est seulement quand j'ai le .apb que je peux déboguer mon Leptonica Dll. Aussi, même si elle dit "Pas de .fichier pdb est produit.".apb est en fait généré avec mes paramètres de projet en cours. Le fait d'avoir /APB dans mon linker options en quelque sorte remplacer après avoir spécifié /Z7 lors de la compilation?
Edit: Aussi, je dois mentionner que j'ai suis en mesure de débogage de la bibliothèque statique version de Leptonica même sans APB.
Références
Leptonica est de l'open-source C librairie de Traitement d'Image par Dan Bloomberg disponible à http://www.leptonica.com. - Je fournir les instructions pour construire Leptonica à l'aide de VS2008/VS2010 et également fournir des binaires pour windows.
Voir http://leptonica.com/vs2008doc/building-leptonlib.html et http://leptonica.com/vs2008doc/building-image-libraries.html pour plus de détails sur la manière dont je construis le Leptonica bibliothèques. http://www.leptonica.org/vs2008doc/building-prog-dir.html explique comment je lien ioformats_reg.
Mon Leptonica VS2008 Solution est disponible à http://www.leptonica.com/source/vs2008-1.67.zip. Mon bibliothèques binaires sont dans le fichier zip à http://leptonica.com/source/leptonica-1.67-win32-lib-include-dirs.zip. Le Leptonica sources sont à http://www.leptonica.com/source/leptonlib-1.67.tar.gz
OriginalL'auteur T Powers | 2010-11-13
Vous devez vous connecter pour publier un commentaire.
Le peu qu'il me manquait, c'est que lorsque vous utilisez une DLL il y a deux invocations de l'éditeur de liens, une fois la DLL et une fois pour l'app que les liens avec la DLL. Lorsque vous utilisez les bibliothèques statiques il y a une seule invocation de l'éditeur de liens (création des bibliothèques statiques utilise LIB).
Donc une DLL liens vers une Bibliothèque d'Exécution C séparément à partir de n'importe quelle application que les liens avec cette DLL. Et les problèmes se produisent si ces deux C temps de fonctionnement sont différents.
Je peux utiliser le VS2010 débogueur de regarder ce que les modules sont chargés via le Debug -> Windows -> les Modules de la fenêtre. Quand j'en lien avec la Leptonica bibliothèques statiques je vois msvcrt.dll et msvcr100d.dll. Cependant, quand je suis le lien avec la Leptonica leptonlibd.dll je peux voir msvcrt.dll, msvcr90d.dll et msvcr100d.dll.
De course "dumpbin importations leptonlibd.dll" montre aussi la référence à msvcr90d.dll.
Je dirais il y a 3 solutions au problème:
Les gens peuvent lier statiquement avec Leptonica pour éviter le problème entièrement.
D'approvisionnement VS2008 et VS2010 versions de leptonlib.dll.
Changer le leptonica API de sorte que toute les descripteurs de FICHIERS ou de mémoire allouée c'
crée ne peut être manipulé/libérées à l'aide de l'API. J'ai posté une question à ce sujet:
http://code.google.com/p/leptonica/issues/detail?id=45
Maintenant que je comprends la cause du problème, je vais aussi probablement fournir un VS2010 version de la DLL dans ma prochaine version binaire.
J'ai décidé de ne pas s'inquiéter de ne pas être en mesure de déboguer le fichier DLL sans un APB. Les personnes qui ont besoin de déboguer Leptonica aura les sources et peuvent construire leurs propres versions de débogage de la bibliothèque (et va donc faire un APB).
Je serais toujours intéressé à entendre si son possible pour les propriétaires de VS2010 pour utiliser le v90 Plate-forme d'Outils option, même si elles n'ont pas VS2008 installé. (Mais plus j'y pense et plus je doute fort qu'ils le peuvent.)
OriginalL'auteur
Vous pouvez lier à 2008 code à l'aide de 2010. Cependant, comme vous l'avez répondu vous-même, si vous créez un objet (par exemple, un mémoire ou un descripteur de fichier) à l'aide d'un moteur d'exécution (2008) et le transmettre à un autre moment de l'exécution (2010) pour le détruire, vous aurez des problèmes - ces systèmes sont distincts des instances (par exemple la gestion de leur propre segment de mémoire), donc ne fonctionnera pas si vous essayez d'utiliser deux d'entre eux de façon interchangeable, comme vous le serez de passage de bloc de mémoire pointeurs vers un système qui n'a aucune idée de ce qu'ils sont ou d'où ils sont venus.
Les solutions sont soit:
assurez-vous que tous ces appels se produire dans un côté ou de l'autre (donc, si votre dll alloue de la mémoire, ils doivent encapsuler que les processus et de fournir des Api pour désallouer trop). Cette internalisation est une bonne conception de la bibliothèque principe en tout cas.
fournir un 2010 version de votre fichier dll pour 2010, les utilisateurs lien. C'est la solution la plus simple pour tout le monde que le marinage autour avec les options du linker n'est tout simplement pas amusant. Forcer les gens à cibler leur code pour un vieux moteur d'exécution afin de pouvoir utiliser votre bibliothèque peut rendre la vie impossible (dès qu'ils veulent utiliser une autre bibliothèque qui fait la même chose, ils sont coincés). Bonnes bibliothèques sont conformes et facile à utiliser, et non normatif et difficile.
Comme pour apb: la Compilation et la liaison sont deux processus différents qui sont en pipeline ensemble. Si vous modifiez les paramètres de compilation, vous devrez peut-être modifier les paramètres de la liaison d'une manière compatible et avant que l'ensemble du pipeline est configuré correctement.
OriginalL'auteur
Désolé pour poster une question comme une réponse, mais...
J'ai le même problème, sauf que tout est dans Visual Studio 2010!
Je suis en utilisant le tesseract OCR bibliothèque qui utilise leptonica. Pour éviter DLL dépendances, j'ai lié le tout de manière statique avec un CRT statique. Il termine aussi un DLL à partir de laquelle j'expose quelques fonctions.
Quand je lien et de construire un programme de test, je peux parcourir le code, et voir que la partie où tesseract appels fopen() fonctionne mais quand elle est appelée à partir de l'intérieur de leptonica code, il se bloque!
J'avais besoin de toute dépendance à l'intérieur d'une seule DLL compilée, afin que je puisse l'utiliser à partir de n'importe quelle langue/plate-forme par le biais d'un extern "C" de l'API. leptonica j'ai recompilé avec les CRT statique, et donc aussi de tesseract. En d'autres mots, toutes les dépendances sont tous des "Multithread Debug" et "Multithread" w.r.t. la bibliothèque d'exécution de l'option. L'idée était que la finale de la DLL ne doit pas dépendre de l'une quelconque des MSVC*.DLL
Hmmm. Dans le VS2010 Débogueur, qu'est-ce que le CRT nom dans la fenêtre Pile des Appels lorsque fopen() est appelée à partir de tesseract vs lors de l'appel de Leptonica se bloque? Ce CRT module(s) sont chargés dans la Fenêtre Modules? Leptonica v1.68 abordera mon problème d'origine... vous risquez d'attendre jusqu'à ce qu'il et tesseract-ocr v3.01 sortir et de voir si le problème persiste. Si oui, les problèmes de fichier est code.google.com/p/leptonica/issues/list et code.google.com/p/tesseract-ocr/issues/list avec tous les détails. Je suis également intéressé à faire en sorte tesseract-ocr utilisation de Leptonica œuvres (sur Windows XP au moins).
OriginalL'auteur
Je pense qu'il serait possible de les utiliser facilement un .dll. Si elles ont le même .Net runtime.
Si vous n'avez pas la possibilité de recompiler le .dll, alors c'est une autre histoire.
OriginalL'auteur