Aller au contenu

[C] [C++] Erreur lors de l'inclusion d'une librairie


Lemst

Messages recommandés

Bonjour à tous,

je dois faire un TP en C et inclure une libraire donnée par le prof: libFicClients.lib.

Lorsque je vais dans les propriétés du projet, éditeur de liens, répertoire de bibliothèques supplémentaires, je mets le chemin. Disons "c:\" pour l'exmple.

Puis dans dépendance supplémentaires, il y a déjà "kernel32.lib", je rajoute "libFicClients.lib".

Lorsque je compile le programme, j'ai une erreur d'exécution "le programme n'a pas pu démarrer blablabla...".

Si je vire mon *.lib, je n'ai plus l'erreur mais le programme ne marche pas.

Quelqu'un pourrait me donner un coup de main s'il vous plait?

Lien vers le commentaire
Partager sur d’autres sites

Quel compilateur/ IDE?

Il doit y avoir le fichier .lib mais aussi un fichier d'exportation (.def sous Visual). C'est ce dernier qui va dire au linker quelles procédures/ fonctions/ classes/ namespaces/ etc se trouvent dans ta librairie.

Le linker n'est pas Simon McKay :francais:

Édit: tu peux faire cela de manière explicite ou ici pour linux (et un peu Windows)

> Lorsque je compile le programme, j'ai une erreur d'exécution "le programme n'a pas pu démarrer blablabla...".

Il faudrait avoir le message complet, mais je soupçonne une différence de paramètres de compilation\ linkage entre ton programme et ta librairie.

> Si je vire mon *.lib, je n'ai plus l'erreur mais le programme ne marche pas.

Impossible: si ton code source utilise cette librairie (via les headers) le linkage doit retourner une erreur.

Lien vers le commentaire
Partager sur d’autres sites

> Lorsque je compile le programme, j'ai une erreur d'exécution "le programme n'a pas pu démarrer blablabla...".

Précisément, ce n'est pas plutôt lorsque tu lances le programme que tu obtiens cette erreur, plutôt qu'à la compilation ?

Auquel cas, ça ressemble beaucoup à une DLL absente. Sous Windows, certains .lib (comme kernel32.lib d'ailleurs) sont en fait juste là pour te permettre de compiler un programme mais ne contiennent pas le code. Le code se trouve en réalité dans une DLL qui porte le même nom (kernel32.dll par exemple) et que le système va charger au lancement de ton programme. Lorsqu'il n'y arrive pas, il affiche effectivement qqchose qui ressemble à "Le programme n'a pas pu démarrer car la bibliothèque de liaison dynamique schtroumpf.dll est introuvable et patati et patata".

Dans ton cas, ça ressemble vraiment à ce que libFicClients.lib est en fait juste là pour forcer le chargement d'un éventuel libFicClients.dll.

Lien vers le commentaire
Partager sur d’autres sites

> Lorsque je compile le programme, j'ai une erreur d'exécution "le programme n'a pas pu démarrer blablabla...".

Précisément, ce n'est pas plutôt lorsque tu lances le programme que tu obtiens cette erreur, plutôt qu'à la compilation ?

Auquel cas, ça ressemble beaucoup à une DLL absente. Sous Windows, certains .lib (comme kernel32.lib d'ailleurs) sont en fait juste là pour te permettre de compiler un programme mais ne contiennent pas le code. Le code se trouve en réalité dans une DLL qui porte le même nom (kernel32.dll par exemple) et que le système va charger au lancement de ton programme. Lorsqu'il n'y arrive pas, il affiche effectivement qqchose qui ressemble à "Le programme n'a pas pu démarrer car la bibliothèque de liaison dynamique schtroumpf.dll est introuvable et patati et patata".

Dans ton cas, ça ressemble vraiment à ce que libFicClients.lib est en fait juste là pour forcer le chargement d'un éventuel libFicClients.dll.

Tu en es sûr de ce que tu dis. Je pense que cela dépend plus de l'option "Runtime Library" (Visual) qui va linker soit en statique (et donc utiliser les .lib) soit en dynamique (et donc utiliser les .dll (sans parler des variantes <Debug/ Release> et <Multi-threadée ou pas>).

Mais dans son cas en forçant/ spécifiant la librairie "libFicClients.lib" dans l'option "Additional Dependencies" (Visual), le linker doit la prendre tel quelle.

Lien vers le commentaire
Partager sur d’autres sites

> Lorsque je compile le programme, j'ai une erreur d'exécution "le programme n'a pas pu démarrer blablabla...".

Précisément, ce n'est pas plutôt lorsque tu lances le programme que tu obtiens cette erreur, plutôt qu'à la compilation ?

Auquel cas, ça ressemble beaucoup à une DLL absente. Sous Windows, certains .lib (comme kernel32.lib d'ailleurs) sont en fait juste là pour te permettre de compiler un programme mais ne contiennent pas le code. Le code se trouve en réalité dans une DLL qui porte le même nom (kernel32.dll par exemple) et que le système va charger au lancement de ton programme. Lorsqu'il n'y arrive pas, il affiche effectivement qqchose qui ressemble à "Le programme n'a pas pu démarrer car la bibliothèque de liaison dynamique schtroumpf.dll est introuvable et patati et patata".

Dans ton cas, ça ressemble vraiment à ce que libFicClients.lib est en fait juste là pour forcer le chargement d'un éventuel libFicClients.dll.

Tu en es sûr de ce que tu dis. Je pense que cela dépend plus de l'option "Runtime Library" (Visual) qui va linker soit en statique (et donc utiliser les .lib) soit en dynamique (et donc utiliser les .dll (sans parler des variantes <Debug/ Release> et <Multi-threadée ou pas>).

Mais dans son cas en forçant/ spécifiant la librairie "libFicClients.lib" dans l'option "Additional Dependencies" (Visual), le linker doit la prendre tel quelle.

L'option Runtime Library ne concerne que MSVCRT.DLL et ses variantes. Quand on compile une DLL, on obtient aussi un .lib qui est en fait le "fantôme" du .dll qui y correspond. Si tu linkes un programme à ce .lib, la compilation s'effectuera nickel chrome, mais le lancement du .exe nécessite le chargement de la DLL.

Ce que j'avais en tête c'est que peut etre le prof avait donné un .lib de ce type, et non un .lib complet (le vilain !!!).

Quoiqu'il en soit foetus a raison : le message complet serait le bienvenu.

Lien vers le commentaire
Partager sur d’autres sites

Je viens de vérifier et effectivement, il y a au moins 3 modes de linkage:

1) Dynamique avec la DLL: le programme va appeler les méthodes/ procédures/ fonctions/ autres de la DLL à l'exécution

2) Statique Dynamique avec le .lib qui appelle la DLL: le .lib contient uniquement des instructions pour le linker du type "telle fonction se trouve dans telle DLL à tel endroit"

3) Statique avec seulement le .lib: le .lib (qui contient tout le code compilé) est copié dans l'exécutable

Les fichiers d'exportation .def ne doivent plus être utilisés: je n'arrive pas à voir si cela correspond à un mode de linkage existant (je dirai le 2) ou à un nouveau: :zarb:

Mais cela veut dire que je suis un dinosaure :francais: ou :fumer:

Mais en cherchant un peu je suis arrivé sur ce thread qui parle du JIT (Just-In-Time)

On peut effectivement utiliser une DLL de cette manière, c'est notamment ainsi que l'on fabrique les plug-ins. C'est ce que l'on appelle le chargement JIT (Just-In-Time) : cela peut offrir un intérêt non négligeable, mais ce n'est pas obligatoire. On peut aussi se lier à une DLL de façon tout à fait définitive (liaison statique).

Dans le cas d'un chargement JIT, ton programme peut tourner même en l'absence de la DLL. Certes, il ne pourra pas profiter des fonctions implémentées dans la DLL, mais ton programme tourne. Par exemple, il peut fonctionner dans un mode basique et/ou "compatible", et ne profiter de fonctions évoluées qu'avec la bonne DLL.

Inconvénients : il est impossible de savoir, à priori, de quelles DLL ton programme aura besoin si elles sont liées de cette manière. C'est un avantage pour des plug-ins, c'est un gros inconvénient pour des fonctions essentielles.

Dans le cas d'une liaison statique, la DLL est référencée "en dur" dans l'entête de l'image exécutable. On peut savoir quelles sont les DLL d'un programme liées ainsi, via l'outil Dependancy Walker. L'avantage, c'est que l'on sait tout de suite s'il manque une DLL à ton programme ou pas.

L'inconvénient, c'est que sans cette DLL, ton programme ne démarre pas du tout, et tu as un message d'erreur système t'indiquant la DLL manquante.

Dans les deux cas, l'initialisation de la DLL prends le même temps, tout comme l'importation des fonctions. Simplement, la première méthode te fait faire le boulot, la seconde est transparente pour le développeur.

Es-tu sûr de ne pas faire du C/C++ managé (.Net)?

Parce que cela correspond à ton cas:

1) Lorsque tu as le .lib, il compile correctement, mais ne peut pas être exécutée parce qu'il y a un delta dans les options de compilation/ linkage (Multi-threadé, Debug, What eles...)

2) Sans le .lib, il linke normal, mais à chaque appel il ne fait rien puisqu'il ne trouve pas la DLL (normal aussi)

Lien vers le commentaire
Partager sur d’autres sites

Oui désolé, c'est sous Visual Studio 2005.

Je ne saurais te répondre, je débute à peine.

lorsque dans les entrées de bibliothèques supplémentaires, je n'ai que kernel32.lib, voici ce qui s'affiche:

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
gereClients.obj : error LNK2019: symbole externe non résolu "int __cdecl getNumberClient(struct _iobuf *)" (?getNumberClient@@YAHPAU_iobuf@@@Z) référencé dans la fonction "struct CpteCLIENT * __cdecl createTabClients(struct _iobuf *)" (?createTabClients@@YAPAUCpteCLIENT@@PAU_iobuf@@@Z)
C:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\Debug\TP3.exe : fatal error LNK1120: 1 externes non résolus
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 2 erreur(s), 1 avertissement(s)
========== Génération : 0 a réussi, 1 a échoué, 0 mis à jour, 0 a été ignoré ==========

Si je rajoute libFicClients.lib à côté de kernel32.lib, j'ai :

Message d'erreur "le programme n'a pas pu démarrer blablabla" et

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
libFicClients.lib(lectureClientFile.obj) : warning LNK4099: PDB 'vc90.pdb' n'a pu être trouvé avec 'libFicClients.lib' ou sur 'c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\debug\vc90.pdb' ; l'objet sera lié sans informations de débogage
Incorporation du manifeste en cours...
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 0 erreur(s), 2 avertissement(s)
========== Génération : 1 a réussi, 0 a échoué, 0 mis à jour, 0 a été ignoré ==========

Pareil si je ne mets que libFicClients.lib dans les bibliothèques.

Lien vers le commentaire
Partager sur d’autres sites

Oui désolé, c'est sous Visual Studio 2005.

Je ne saurais te répondre, je débute à peine.

lorsque dans les entrées de bibliothèques supplémentaires, je n'ai que kernel32.lib, voici ce qui s'affiche:

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
gereClients.obj : error LNK2019: symbole externe non résolu "int __cdecl getNumberClient(struct _iobuf *)" (?getNumberClient@@YAHPAU_iobuf@@@Z) référencé dans la fonction "struct CpteCLIENT * __cdecl createTabClients(struct _iobuf *)" (?createTabClients@@YAPAUCpteCLIENT@@PAU_iobuf@@@Z)
C:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\Debug\TP3.exe : fatal error LNK1120: 1 externes non résolus
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 2 erreur(s), 1 avertissement(s)
========== Génération : 0 a réussi, 1 a échoué, 0 mis à jour, 0 a été ignoré ==========

Si je rajoute libFicClients.lib à côté de kernel32.lib, j'ai :

Message d'erreur "le programme n'a pas pu démarrer blablabla" et

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
libFicClients.lib(lectureClientFile.obj) : warning LNK4099: PDB 'vc90.pdb' n'a pu être trouvé avec 'libFicClients.lib' ou sur 'c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\debug\vc90.pdb' ; l'objet sera lié sans informations de débogage
Incorporation du manifeste en cours...
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 0 erreur(s), 2 avertissement(s)
========== Génération : 1 a réussi, 0 a échoué, 0 mis à jour, 0 a été ignoré ==========

Pareil si je ne mets que libFicClients.lib dans les bibliothèques.

et le message d'erreur complet au démarrage de ton programme c'est quoi ?

Lien vers le commentaire
Partager sur d’autres sites

lorsque dans les entrées de bibliothèques supplémentaires, je n'ai que kernel32.lib, voici ce qui s'affiche:

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
gereClients.obj : error LNK2019: symbole externe non résolu "int __cdecl getNumberClient(struct _iobuf *)" (?getNumberClient@@YAHPAU_iobuf@@@Z) référencé dans la fonction "struct CpteCLIENT * __cdecl createTabClients(struct _iobuf *)" (?createTabClients@@YAPAUCpteCLIENT@@PAU_iobuf@@@Z)
C:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\Debug\TP3.exe : fatal error LNK1120: 1 externes non résolus
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 2 erreur(s), 1 avertissement(s)
========== Génération : 0 a réussi, 1 a échoué, 0 mis à jour, 0 a été ignoré ==========

Il ne trouve pas la fonction getNumberClient appelée dans la fonction createTabClients. Donc pour moi c'est normal :D

Si je rajoute libFicClients.lib à côté de kernel32.lib, j'ai :

Message d'erreur "le programme n'a pas pu démarrer blablabla" et

------ Début de la génération : Projet : TP3, Configuration : Debug Win32 ------
Édition des liens en cours...
LINK : warning LNK4067: point d'entrée ambigu ; 'mainCRTStartup' sélectionné
libFicClients.lib(lectureClientFile.obj) : warning LNK4099: PDB 'vc90.pdb' n'a pu être trouvé avec 'libFicClients.lib' ou sur 'c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\debug\vc90.pdb' ; l'objet sera lié sans informations de débogage
Incorporation du manifeste en cours...
Le journal de génération a été enregistré à l'emplacement "file://c:\Documents and Settings\Administrateur\Mes documents\Visual Studio 2005\Projects\TP3\TP3\Debug\BuildLog.htm"
TP3 - 0 erreur(s), 2 avertissement(s)
========== Génération : 1 a réussi, 0 a échoué, 0 mis à jour, 0 a été ignoré ==========

Fixing the Warning PDB ‘vc90.pdb’ not found

Ou alors Linker Tools Warning LNK4099

errorvc.png

Il y a un problème avec le point d'entrée (Linker -> Advanced): Il en a plusieurs et il a choisi celui ci mainCRTStartup.

Et je pense que le problème vient de là: mainCRTStartup ne doit pas être un point d'entrée ou ne pas exister :zarb:.

Cela, pour moi, peut confirmer que soit tu t'es trompé en choisissant ton type de projet (de type .Net) soit libFicClients.lib a été compilée avec des options différentes de ton projet, voire même que ce n'est pas une librairie de type .lib.

Lien vers le commentaire
Partager sur d’autres sites

ta supposition "a été compilée avec des options différentes" m'a mis sur la voie.

J'ai essayé de récupérer la première partie rendue au prof et faite en cours. Elle n'était pas reconnue par ma version. En fait, il fallait Visual C++ 2008 !

Merci pour votre aide les gars :)

Lien vers le commentaire
Partager sur d’autres sites

ta supposition "a été compilée avec des options différentes" m'a mis sur la voie.

J'ai essayé de récupérer la première partie rendue au prof et faite en cours. Elle n'était pas reconnue par ma version. En fait, il fallait Visual C++ 2008 !

Merci pour votre aide les gars :)

La différence entre Visual 2005 et Visual 2008 est la version du .Net. Donc, pour le C/ C++ natif (managé je ne sais pas), il n'y a rien de nouveau (ou alors 3 fois rien).

Si des nouveaux contrôles sauce Vista dans les MFC (si je ne me trompes pas) :francais:

Et effectivement comme le signale le linker, la librairie libFicClients.lib a été compilée en release avec Visual 2008 (vc90.pdb).

Enfin, je pense qu'il faudrait que tu fasses la différence entre les options de ton projet qui marche avec celui qui ne marche pas: cela peut être instructif pour toi.

:contourne:

Lien vers le commentaire
Partager sur d’autres sites

Archivé

Ce sujet est désormais archivé et ne peut plus recevoir de nouvelles réponses.

×
×
  • Créer...