Posts Tagged ‘Visual Studio’
Linkage Qt sous Visual Studio : libgles_cm.lib
11 décembre 2011J’ai acquis récemment une nouvelle machine pour le développement. Je fais notamment du développement sous Visual Studio 2008 avec Qt, grâce à l’add-in Qt pour Visual Studio. J’ai donc importé mes projets après avoir réinstallé l’ensemble de mes outils. A la première compilation, l’erreur suivante survient lors de l’étape de l’édition des liens :
Après enquête, la solution est la suivante : sous Visual Studio : menu Projet –> Propriétés du projet –> Propriété de configuration (barre latérale à droite) –> Editeur de liens –> Entrée –> supprimer la bibliothèque problématique (libgles_cm.lib) dans la zone « Dépendances supplémentaires ».
Cette bibliothèque n’était pas présente dans mon projet initial, j’ignore donc pourquoi cette dépendance à été ajoutée de façon automatique et à mon insu… Il s’agit a priori d’une bibliothèque OpenGL. La seule différence entre les deux configuration des machines étant le passage de Qt 4.6.3 à 4.6.4.
Utilisation de GeographicLib sous Visual Studio C++
21 octobre 2011Je vous livre ici la solution à un problème qui m’a donné pas mal de fil à retordre : l’utilisation de la librairie GeographicLib (une bibliothèque de calcul de coordonnés géographique, notamment du « direct geodesic problem« , qui consiste à calculer une positon sur la Terre en connaissant une positon d’origine, une distance et un azimut(cap). Cette bibliothèque est également capable de faire des conversions entre les différents systèmes géodesiques existants). Je précise que la version utilisées ici est la 1.14
Mes problèmes furent multiples :
- Faire fonctionner la bibliothèque sous Visual Studio (2008 pour mon cas, mais les soucis auraient probablement étés les mêmes sous VS2005 ou VS2010)
- Comprendre comment elle fonctionne
- Réussir à compiler, en l’occurrence, j’avais des erreurs sur l »édition des liens (linker).
1) Installer et faire fonctionner la librairie sous VC2008
Pas de grosses difficultés ici, il faut juste ne pas se faire piéger par la doc qui présente (à ce jour) une erreur. Donc :
- dans les paramètres du projet (Projet -> Propriété de…),
- se rendre dans Propriété de configuration ->C/C++->Général->Autres répertoire include et renseigner : C:Program FilesGeographicLib-1.14include.
- Dans Éditeur de liens->Général-> Répertoires de bibliothèques supplémentaires, renseigner C:Program FilesGeographicLib-1.14lib et non C:Program FilesGeographicLib-1.14include comme indiqué dans la documentation
- Dans Éditeur de liens->Entrée->Dépendances supplémentaires, ajouter Geographic.lib
2) Comprendre comment elle fonctionne
Ici, j’ai eu des difficultés, car c’est l’une des premières fois que j’utilise une bibliothèque tierce (hors Qt, superbe doc, et SDK matériels, qui ont souvent eut aussi une doc assez explicite avec des exemples), et assez peu utilisée. J’ai donc eu un mal terrible à trouver des exemples sur Internet. Lors de mes premiers essais, j’ai ainsi codé ainsi :
double lon1 = 6.327472;
double azi1 = 59.16;
double s12 = 6216.28;
double lat2;
double lon2;
Geodesic::Direct(lat1, lon1, azi1, s12, &lat2, &lon2);
Ce qui générait à la compilation des erreurs du genre :
.GeographicLib/Geodesic.hpp(350): peut être 'GeographicLib::Math::real GeographicLib::Geodesic::Direct(GeographicLib::Geodesic::real,GeographicLib::Geodesic::real,GeographicLib::Geodesic::real,GeographicLib::Geodesic::real,GeographicLib::Geodesic::real &,GeographicLib::Geodesic::real &) throw() const'
Je vous livre donc la syntaxe correcte qui est :
double lon1 = 6.327472;
double azi1 = 59.16;
double s12 = 6216.28;
double lat2;
double lon2;
const Geodesic& g = Geodesic::WGS84;
g.Direct(lat1, lon1, azi1, s12, lat2, lon2);
3) Parvenir à compiler/linker
A la compilation, enfin, à l’édition des liens pour être précis, j’obtenais les erreurs suivantes :
1>Geographic.lib(Geodesic.obj) : warning LNK4229: directive '/FAILIFMISMATCH:_MSC_VER=1600' non valide rencontrée ; ignorée
1>Geographic.lib(Geodesic.obj) : warning LNK4229: directive '/FAILIFMISMATCH:_ITERATOR_DEBUG_LEVEL=0' non valide rencontrée ; ignorée
1>Geographic.lib(GeodesicLine.obj) : warning LNK4229: directive '/FAILIFMISMATCH:_MSC_VER=1600' non valide rencontrée ; ignorée
1>Geographic.lib(GeodesicLine.obj) : warning LNK4229: directive '/FAILIFMISMATCH:_ITERATOR_DEBUG_LEVEL=0' non valide rencontrée ; ignorée
1>msvcprt.lib(MSVCP90.dll) : error LNK2005: "public: __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::~basic_string<char,struct std::char_traits<char>,class std::allocator<char> >(void)" (??1?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE@XZ) déjà défini(e) dans Geographic.lib(Geodesic.obj)
1>msvcprt.lib(MSVCP90.dll) : error LNK2005: "public: char const * __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::c_str(void)const " (?c_str@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBEPBDXZ) déjà défini(e) dans Geographic.lib(Geodesic.obj)
1>msvcprt.lib(MSVCP90.dll) : error LNK2005: "public: class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > & __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::erase(unsigned int,unsigned int)" (?erase@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAEAAV12@II@Z) déjà défini(e) dans Geographic.lib(Geodesic.obj)
1>msvcprt.lib(MSVCP90.dll) : error LNK2005: "public: __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >(char const *)" (??0?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QAE@PBD@Z) déjà défini(e) dans Geographic.lib(Geodesic.obj)
1>msvcprt.lib(MSVCP90.dll) : error LNK2005: "public: static unsigned int __cdecl std::char_traits<char>::length(char const *)" (?length@?$char_traits@D@std@@SAIPBD@Z) déjà défini(e) dans Geographic.lib(Geodesic.obj)
1>Geographic.lib(Geodesic.obj) : error LNK2019: symbole externe non résolu "__declspec(dllimport) void __cdecl std::_Xlength_error(char const *)" (__imp_?_Xlength_error@std@@YAXPBD@Z) référencé dans la fonction "public: void __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::_Xlen(void)const " (?_Xlen@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBEXXZ)
1>Geographic.lib(Geodesic.obj) : error LNK2019: symbole externe non résolu "__declspec(dllimport) void __cdecl std::_Xout_of_range(char const *)" (__imp_?_Xout_of_range@std@@YAXPBD@Z) référencé dans la fonction "public: void __thiscall std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> >::_Xran(void)const " (?_Xran@?$basic_string@DU?$char_traits@D@std@@V?$allocator@D@2@@std@@QBEXXZ)
Après pas mal de lecture sur le net et avoir bidouillé a peu près tous les paramètres de l’éditeur de liens de Visual Studio, je me suis résolu à recompiler moi même la librairie. Pour cela, il faut télécharger le zip du code source de GeographicLib (ici par exemple). Les développeurs ont même eu l’idée de fournir des fichiers projets pour VS2005 (GeographicLib-vc8.sln), 2008 (GeographicLib-vc9.sln) et 2010 (GeographicLib-vc10.sln) (répertoire windows de l’archive). J’ouvre donc le fichier qui correspond à ma version de Visual Studio et j’ai compilé la bibliothèque en mode Release. Il en ressort un beau fichier .lib d’environ 1800 ko (contre 1300 ko pour celui fourni). Après remplacement du fichier Geographic.lib fourni par ce nouveau fichier, la compilation et l’édition des liens se déroule à merveille, et la bibliothèque semble fonctionner.
Dans mon immense bonté, je vous fourni cette librairie compilée avec Visual Studio C++ 2008 (je ne sais pas si elle fonctionne avec VC2005 ou VC2010) : Geographic.lib.
InnoSetup : ajouter les DLL Visual C++
14 octobre 2011Si vous développez à l’aide de Microsoft Visual Studio, vos programmes nécessitent, pour fonctionner sur une machine quelconque, de diposer des bibliothèques suivantes (DLL de VC++ 2008) :
- mfc90.dll
- msvcr90.dll
- msvcp90.dll
- atl90.dll
- vcomp.dll
- Téléchargez vcredist_x86.exe sur le site de Microsoft (voir lien plus haut) et enregistrez le dans un sous dossier ./bin/ de votre projet
- Ouvrez votre projet Inno Setup (je suppose ici que celui-ci est d’hors et déjà créé et que l’emplacement des autres fichiers de votre projet sont déjà renseignés)
- Dans la section [files] de votre projet, ajoutez ceci :
Source: "{src}binvcredist_x86.exe"; DestDir: "{app}bin"; Flags: deleteafterinstall
- Dans la section [Run], ajoutez :
Filename: "{app}binvcredist_x86.exe"; Parameters: "/q:a /c:""VCREDI~3.EXE /q:a /c:""""msiexec /i vcredist.msi /qn"""" """; WorkingDir: "{app}bin"; StatusMsg: Installing VCREDIST...