IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C++ Discussion :

création d'une dll incluant une classe c++ avec mingw32


Sujet :

C++

  1. #1
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 14
    Points : 10
    Points
    10
    Par défaut création d'une dll incluant une classe c++ avec mingw32
    Bonjour à tous,

    Alors voilà, j'ai un problème qui m'agasse depuis un petit bout de temps...
    J'ai du code c++ que je veux faire tourner sous linux, mac et win... je ne veux pas donner mon code, donc, je crée des librairies. Sous linux pas de problème, mais pour créer des dll qui fonctionnent correctement c'est la galère !
    voilà un exemple bidon de classe :


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
     
    //--------------------------------------------------------------------
    // Fichier .h
     
    #ifndef __TEST_TOOL_H__
    #define __TEST_TOOL_H__
     
    #include "StdAfx.h" // Modifié pour passer aussi sous linux
     
    #ifdef TEST_TOOL_DLL_EXPORTS
    #define TEST_TOOL_API     __declspec(dllexport)
    #else
    #define TEST_TOOL_API     __declspec(dllimport)
    #pragma message("**** Importation de la DLL (2) ****")
    #endif
     
    #include <stdio.h>
    #include <stdlib.h>
     
    class TEST_TOOL_API  CTest
    {
    public:
    	CTest();                                                   
    	~CTest();
    	void Somme();
     
    public:
    	int a;
    	int b;
    	int c;
    };
     
    #endif
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
     
    //--------------------------------------------------------------------
    // Fichier de la dll .cpp
     
    #include "TestLib.h"
     
    CTest::CTest()
    {
    	a = 2;
    	b = 6;
    	c = 0;
    }
     
     
    CTest::~CTest()
    {
    }
     
    void CTest::Somme()
    {
    	c = a + b;
    	printf("\n **** %d + %d = %d ****\n",a,b,c);
    }
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    # Makefile de la dll (exécuté sur mingw32) 
    ...
    library: obj
    	$(MKDIR) $(LIB_DIR_LIB)
    	ar rc $(LIB_DIR_LIB)/lib$(LIB_TEST_NAME).a $(LIB_DIR_SRC)/$(LIB_TEST_NAME).o 
    	ranlib $(LIB_DIR_LIB)/lib$(LIB_TEST_NAME).a
    	g++ -shared -o $(LIB_DIR_LIB)/$(LIB_TEST_NAME).dll $(LIB_DIR_SRC)/$(LIB_TEST_NAME).o -Wl,--kill-at,--output-def,$(LIB_DIR_SRC)/$(LIB_TEST_NAME).def   
    	dllwrap --def $(LIB_DIR_SRC)/$(LIB_TEST_NAME).def -o $(LIB_DIR_LIB)/$(LIB_TEST_NAME).dll $(LIB_DIR_SRC)/$(LIB_TEST_NAME).o
    ...

    Fichier .def généré par le makefile :

    EXPORTS
    _ZN5CTest5SommeEv @1
    _ZN5CTestC1Ev @2
    _ZN5CTestC2Ev @3
    _ZN5CTestD1Ev @4
    _ZN5CTestD2Ev @5

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    //--------------------------------------------------------------------
    // Fichier principal
    #include "TestLib.h"
     
    int main(int argc, char* argv[])
    {
    	CTest *_Test = new CTest();
    	_Test->Somme();
    	return 0;
    }

    Message d'erreur de visual c++ :

    --------------------Configuration: test3 - Win32 Debug--------------------
    Linking...
    Creating library Debug/test3.lib and object Debug/test3.exp
    test3.obj : error LNK2001: unresolved external symbol "public: void __thiscall CTest::Somme(void)" (?Somme@CTest@@QAEXXZ)
    test3.obj : error LNK2001: unresolved external symbol "public: __thiscall CTest::CTest(void)" (??0CTest@@QAE@XZ)
    Debug/test3.exe : fatal error LNK1120: 2 unresolved externals
    Error executing link.exe.

    test3.exe - 3 error(s), 0 warning(s)


    Je souhaite donc compiler ma dll sous mingw32 et l'intégrer dans visual c++.
    Je suis un peu perdu là... j'ai essayé un nombre considérable de solutions et rien ne passe. Par contre si la dll est crée sous visual, tout se déroule sans problème. De même une dll en C (en utilisant extern "C") fonctionne correctement.

    Je pense que c'est un problème de nom de fonction (voir .def). Car la compilation se passe bien, mais pas lédisiotn de liens.
    qqun peut-il m'éclairer ?
    merci

  2. #2
    Membre du Club
    Inscrit en
    Septembre 2003
    Messages
    49
    Détails du profil
    Informations forums :
    Inscription : Septembre 2003
    Messages : 49
    Points : 43
    Points
    43
    Par défaut
    Salut
    Le probleme en c++ c'est que le standard ne stipule rien sur la decoration des fonctions (nom donne a ces fonction par le compilateur en interne). en C c'est bien defini. Donc si tu cree une dll sur un compiletur X il y a beacoup de chance qu'elle ne soit pas reconnu par un compilateur Y. le seul moyen d'y remedier est de lui fournir une interface en C
    a+

  3. #3
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 14
    Points : 10
    Points
    10
    Par défaut
    Ok... je vois le problème... j'avais essayé un truc dans le genre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    class CTest
    {
    public:
    	CTest();                                                   
    	~CTest();
    	void Somme();
     
    public:
    	int a;
    	int b;
    	int c;
    };
     
    extern "C" TEST_TOOL_API CTest* get_new_CTest_Instance();
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    CTest::CTest()
    {
    	a = 2;
    	b = 6;
    	c = 0;
    }
     
     
    CTest::~CTest()
    {
    }
     
    void CTest::Somme()
    {
    	c = a + b;
    	printf("\n **** %d + %d = %d ****\n",a,b,c);
    }
     
    CTest* get_new_CTest_Instance() 
    { 
    	return new CTest(); 
    }
    mais le compilateur (mingw32) me dit ceci :

    ...
    g++ -shared -o ../../TestLib3/lib/Win-mingw32/TestLib.dll ../../TestLib3/src/TestLib.o -Wl,--kill-at,--output-def,../../TestLib3/src/TestLib.def
    dllwrap --def ../../TestLib3/src/TestLib.def -o ../../TestLib3/lib/Win-mingw32/TestLib.dll ../../TestLib3/src/TestLib.o
    ../../TestLib3/src/TestLib.o(.text+0xa9):TestLib.cpp: undefined reference to `operator new(unsigned)'
    c:\MyInstallations\MinGW\bin\dllwrap.exe: c:\MyInstallations\MinGW\bin\gcc exited with status 1
    make: *** [library] Error 1

    là encore je ne vois pas bien...

  4. #4
    Expert éminent sénior
    Avatar de Luc Hermitte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2003
    Messages
    5 275
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2003
    Messages : 5 275
    Points : 10 985
    Points
    10 985
    Par défaut Re: création d'une dll incluant une classe c++ avec mingw32
    Citation Envoyé par TheShadow
    Je souhaite donc compiler ma dll sous mingw32 et l'intégrer dans visual c++.
    IIRC, ce n'est pas possible. ABI différentes. Ou alors GCC a fait des progrès.
    Tu risques de devoir livrer autant de bibliothèques précompilées que de compilos cibles.
    Blog|FAQ C++|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS|Bons livres sur le C++
    Les MP ne sont pas une hotline. Je ne réponds à aucune question technique par le biais de ce média. Et de toutes façons, ma BAL sur dvpz est pleine...

  5. #5
    Membre à l'essai
    Profil pro
    Inscrit en
    Octobre 2005
    Messages
    14
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2005
    Messages : 14
    Points : 10
    Points
    10
    Par défaut
    Le problème est résolu :
    J'ai réalisé une interface C pour exporter mes fonctions (avec extern "C") comme je l'ai précisé ici:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
     
     
    #ifndef __TEST_TOOL_H__
    #define __TEST_TOOL_H__
     
    #include "StdAfx.h" // Modifié pour passer aussi sous linux
     
    #ifdef TEST_TOOL_DLL_EXPORTS
    #define TEST_TOOL_API     __declspec(dllexport)
    #else
    #define TEST_TOOL_API     __declspec(dllimport)
    #endif
     
    #include <stdio.h>
    #include <stdlib.h> 
     
    class CTest
    {
    public:
       CTest();                                                   
       ~CTest();
       void Somme();
     
    public:
       int a;
       int b;
       int c;
    };
     
    extern "C" TEST_TOOL_API CTest* get_new_CTest_Instance();

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
     
    CTest::CTest()
    {
       a = 2;
       b = 6;
       c = 0;
    }
     
     
    CTest::~CTest()
    {
    }
     
    void CTest::Somme()
    {
       c = a + b;
       printf("\n **** %d + %d = %d ****\n",a,b,c);
    }
     
    CTest* get_new_CTest_Instance()
    {
       return new CTest();
    }
    et pour créer une dll et un .lib avec lesquels visual C peut s'interfacer, j'ai utilisé :

    Dans le makefile (après création du .o de ma librairie).
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    ...
    g++ -shared -o ma_dll.dll ma_dll.o -Wl,--output-def,ma_dll.def,--out-implib,libma_dll.a
    lib /machine:i386 /def:ma_dll.def
    ...
    Remarque : il est possible d'utiliser directement ma_dll.cpp à la place de ma_dll.o... mais l'utilisation d'un .a ne fonctionne pas.

    L'outil lib.exe (création du .lib) est livré avec visual studio dans le répertoire \Microsoft Visual Studio\VC98\Bin
    (Cela implique donc de faire une version spéciale du makefile pour windows.)
    j'ai maintenant d'autres problème.... mais cela fera l'objets d'un nouveau sujet...

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 1
    Dernier message: 05/03/2012, 11h39
  2. Réponses: 6
    Dernier message: 02/11/2011, 09h34
  3. Réponses: 6
    Dernier message: 10/06/2010, 15h31
  4. Recherche une valeur d'une cellule dans une colonne d'une autre feuille
    Par kourria dans le forum Macros et VBA Excel
    Réponses: 8
    Dernier message: 21/06/2007, 13h48
  5. utiliser une dll dans une dll
    Par anthonycosson dans le forum MFC
    Réponses: 2
    Dernier message: 09/05/2006, 21h42

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo