Rabbi Jakob
Messages postés4Date d'inscriptionvendredi 3 août 2007StatutMembreDernière intervention 7 août 2007
-
6 août 2007 à 16:58
Rabbi Jakob
Messages postés4Date d'inscriptionvendredi 3 août 2007StatutMembreDernière intervention 7 août 2007
-
7 août 2007 à 14:27
Bonjour,
Je programme en c++ sous visual studio 2005
J'ai un petit problème avec ma dll Je dispose d'une dll avec son fichier .lib. Je les ai mis tous les 2 dans le répertoire où se trouve le .exe de mon projet, et j'ai linké la librairie aux projet dans project dépendencies.
Mon problème est le suivant. J'appelle une fonction MaFonction dans ma dll MaDLL.dll.
MaFonction prend en argument une structure MaStructure. MaStructure et MaFonction sont définies dans le fichier header généré avec la dll, MaDll.h.
Si je fais extern "C" __declspec(dllimport) void MaFonction(MaStruct), et que je le place après #include <MaDll.h>, il me lance une erreur C2732, selon laquelle ma fonction est déjà définie ailleurs (ce que je conçois aisément puisqu'elle est dans le .h)
Seulement, si je ne place pas le extern "C" declspec(dllimport)... , et que je mets seulement le fichier .h, il me lance une erreur LNK2001, il ne trouve pas la fonction (unresolved external symbol) Pourtant la librairie est bien linkée. Je ne comprends vraiment pas, j'ai lu la msdn, j'ai fouillé un max de forum, j'ai essayé une autre fonction de la dll qui prend des types simples, et là c'est encore plus étrange
Si je fais le extern "C" _declspec double FonctionSimple (double, double), et que je place ça avant la déclaration des fichiers .h, la fonction sort le bon résultat. Si je le mets après le .h, il me ressort l'erreur C2732 (déjà définie), et je ne mets pas le extern "C"..., il me remet aussi l'erreur LNK2001.
Le problème, c'est que j'ai bosoin de la struct MaStruct, et donc je peux pas mettre extern "C" __declspec(dllimport) void MaFonction(MaStructure) avant la déclaration des fichiers .h, sinon il ne reconnapit pas MaStructure....
Bref, je suis perdu, si quelqu'un a déjà eu un problème comme ça, pensez à un pauvre débutant en informatique
Rabbi Jakob
Messages postés4Date d'inscriptionvendredi 3 août 2007StatutMembreDernière intervention 7 août 20071 7 août 2007 à 14:27
j'ai finalement pu trouver ce qui n'allait pas.
Il y avait dans un fichier en-tête appelé par MaLib.h un #define _FSSAPI_decl __declspec(dllimport) et je l'ai remplacé par _FSSAPI_decl extern"C"__declspec(dllimport)
C'était donc une erreur dans la dl qui m'a été fournie apparemmenr(je dis apparemment, car j'ai juste fait un essai avec 2 fonctions, j'espère que je ne me suis pas trompé).
Merci à SAKingdom pour son attention, bonne journée à tous!!
Peace and tranquillity on earth
PS: Au fait, désolé pour les changements de taille de police dans le poste d'avant, mais je sais pas comment faire un édit pour modifier tout ça.
SAKingdom
Messages postés3212Date d'inscriptionlundi 7 novembre 2005StatutMembreDernière intervention16 février 200915 6 août 2007 à 17:21
Les prototypes de tes fonctions sont déjà dans le .h ?
Si oui, à quoi ça sert de redéclarer le prototype. La fonction devrait être utilisable dès que tu inclus ton .h.
SAKingdom
Messages postés3212Date d'inscriptionlundi 7 novembre 2005StatutMembreDernière intervention16 février 200915 6 août 2007 à 17:23
Ah oups
"Seulement, si je ne place pas le extern "C" declspec(dllimport)... , et que je mets seulement le fichier .h, il me lance une erreur
LNK2001, il ne trouve pas la fonction (unresolved external symbol)"
Rabbi Jakob
Messages postés4Date d'inscriptionvendredi 3 août 2007StatutMembreDernière intervention 7 août 20071 6 août 2007 à 18:04
Oui, j'ai exactement le schéma que tu m'as dit; a priori, je pense que le fichier .h qui m'a été donné est bon, puisque ce n'est pas moi qui l'ai fait lol. Ce que je trouve étrange, c'est que si je ne mets pas le extern "C"declspec(dllimport) FonctionSimple(double, double), que je mette juste le header MaDll.h, et que j'appelle FonctionSimple(1.2), il me sort que FonctionSimple ne fonctionne pas avec un seul double. En revanche, si je mets FonctionSimple(1.2,5..3), là il me met l'erreur LNK2001 comme quoi il ne connaît pas la fonction. De plus, quand je tape FonctionSimple( Visual Studio me met qu'il faut que je rentre 2 doubles. C'est signe qu'il connaît déjà le prototype de la fonction, non? Donc a priori, je ne devrai avoir besoin de réécrire le prototype en début de programme, normalement?
SAKingdom
Messages postés3212Date d'inscriptionlundi 7 novembre 2005StatutMembreDernière intervention16 février 200915 6 août 2007 à 18:52
Les prototypes sont bien déclarés dans le .h. Inutile d'en ajouter.
L'erreur survient lors du linkage. Le linker ne trouve pas la fonction dans les lib que tu lui donne.
Soit la lib n'est pas correcte (ce qui m'étonnerais), soit tu as fais une erreur quand tu l'as ajouté.
Essais d'ajouter ceci dans le code
#pragma comment(lib, "malib.lib")
Rabbi Jakob
Messages postés4Date d'inscriptionvendredi 3 août 2007StatutMembreDernière intervention 7 août 20071 7 août 2007 à 10:07
J'ai essayé ton code, et il me sort cette fois-ci l'erreur LNK2019. J'ai regardé si ça pouvait être dû à une erreur dans la convention d'appel (std_call,...) .J'ai regardé mon fichier .h, parce que le schéma de mon header MaLib.h n'est pas exactement comme celui que tu m'as précisé, les prototypes de mes fonctions se présentent comme ça: _FSSAPI_decl
double FonctionSimple(
double,
double); , il n'y a pas le __stdcall dont tu parlais tout à l'heure. En revanche, dans l'output de mon debugger,, il me marque unresolved external symbol"__declspec(dllimport) double __cdecl FonctionSimple(double, double)". Je pense que c'est parce que les fonctions ne sont pas définies dans une classe. Je ne sais pas si dans ce cas il faut faire une procédure d'appel spécial, ce que m'étonnerait puisque la procédure d'appel __cdecl à l'air d'être la procédure d'appel par défaut.
Je viens aussi d'essayer le #pragma (linker,"/DEFAULTLIB:MaLib.lib"), parce que windows.h redéfinit le type BOOLEAN qui est déjà défini dans MaDll.h (sous winnt.h, BOOLEAN est un BYTE, sous MaLib.h, c'est un char), mais ça n'a pas avancé le problème apparemment.
J'ai aussi essayé d'enlever le header windows.h, pour éviter les rédéfinitions, et là il me ressort l'erreur LNK2019, et de même si je mets le #pragma comment(lib, "MaLib.lib") et que j'enlève MaLib.lib des additional dependencies de mon projet afin d'éviter une éventuelle redéfinition.
En revanche, je ne vois pas trop à quoi cela sert d'ajouter le header windows.h à mon projet. Il est nécessaire à l'appel d'une dll externe?
J'ai enfin essayé une autre solution: comme ma dll a été écrit en C et que je code en C++, j'ai essayé de mettre un extern "C" (sans __declspec(dllimport)) devant le prototype de la fonction, mais là encore sans succès (C2732, redéfinition des fonctions). Je vais regarder en mode verbeux si j'obtiens quelquechose de plus consistant....