2013-07-14 14 views
6

Niedawno nauczyłem się pięknego języka D, który jest bardziej plastyczny i pomaga sobie pisać stabilne szybkie programy. Ale nie jest popularny ... ponieważ kilka kodu napisano na D, a więc więcej na C i C++. Dlatego po przeczytaniu książki Andrei Alexanderscu, gdzie autor bardzo powierzchownie opisał pytanie o łączenie biblioteki D z C++, spróbowałem nauczyć się tego samego i napisałem jakiś kod na D, gdzie zdefiniowana funkcja zwraca instancję klasy CompleteAutomata, która implementuje AutomataInterface zdefiniowana również w C++ Kod:Łączenie biblioteki D z kodem C++

#ifndef AUTOMATAINTERFACE_H 
#define AUTOMATAINTERFACE_H 

class AutomataInterface { 
public: 
    virtual ~AutomataInterface() {} 

    virtual void next() = 0; 

    virtual void save() = 0; 
    virtual void restore() = 0; 
    virtual void zerofile() = 0; 

    virtual void invert(unsigned long x, unsigned long y) = 0; 

    virtual int state(unsigned long x, unsigned long y) const = 0; 

    virtual unsigned long x() const = 0; 
    virtual unsigned long y() const = 0; 
}; 

AutomataInterface *createAutomata(unsigned long x, unsigned long y); 

#endif // AUTOMATAINTERFACE_H 

odpowiedni kod D:

import agregator; // this is my own lib 

extern(C++) { 
    interface AutomataInterface { 
     void next(); 

     void save(); 
     void restore(); 
     void zerofile(); 

     void invert(size_t x, size_t y); 

     int state(size_t x, size_t y) const; 

     size_t x() const; 
     size_t y() const; 
    } 

    AutomataInterface createAutomata(ulong x, ulong y) { 
     return new CompleteAutomata(x, y); 
    } 
} 

export class CompleteAutomata : AutomataInterface { 
    // instance variables... 
    this(size_t x, size_t y) { /* ... */ } 

    extern(C++) { 
     override void next() { 
      // ... 
     } 

     // others overridden interface methods... 
    } 
} 

Po Kod napisał, mam kompilowania biblioteki D przez dwóch różnych kompilatorów (dmd i gdc), z następujących flag:

dmd -release -O -lib -odlib -ofliblife.h *.d 

lub

gdc -frelease -O2 -Wall -c *.d 
ar cq lib/liblife.a *.o 

Kiedy próbuje odnośnik każdego z otrzymanych do projektu bibliotekami Qt, dodając ścieżkę do katalogu biblioteki (-L opcja) i dodanie lib bezpośrednio (-l opcja). Mam błędy w obu przypadkach.

W pierwszym dmd przypadku mam „niezdefiniowana odniesienia do` _d_newclass'”oraz kilka kolejnych błędów:

g++ -Wl,-O1 -Wl,-z,relro -o automata main.o mainwindow.o renderarea.o button.o playbutton.o moc_mainwindow.o moc_renderarea.o moc_button.o moc_playbutton.o -L/home/newmen/projects/d/life/lib -llife -lQtGui -lQtCore -lpthread 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1fe_5b0.o): In function `createAutomata(unsigned int, unsigned int)': 
complete_automata.d:(.text._Z14createAutomatajj+0x27): undefined reference to `_d_newclass' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0x0): undefined reference to `_D14TypeInfo_Class6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0x50): undefined reference to `_D6Object7__ClassZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0xd0): undefined reference to `_D14TypeInfo_Class6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0x120): undefined reference to `_D6Object7__ClassZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x68): undefined reference to `_D6object6Object8toStringMFZAya' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x70): undefined reference to `_D6object6Object6toHashMFNbNeZm' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x78): undefined reference to `_D6object6Object5opCmpMFC6ObjectZi' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x80): undefined reference to `_D6object6Object8opEqualsMFC6ObjectZb' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0xf8): undefined reference to `_D6object6Object8toStringMFZAya' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x100): undefined reference to `_D6object6Object6toHashMFNbNeZm' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x108): undefined reference to `_D6object6Object5opCmpMFC6ObjectZi' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x110): undefined reference to `_D6object6Object8opEqualsMFC6ObjectZb' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o): In function `_D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata': 
complete_automata.d:(.text._D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata+0x1f): undefined reference to `_d_newclass' 
complete_automata.d:(.text._D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata+0x46): undefined reference to `_d_newclass' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o): In function `CompleteAutomata::next()': 
complete_automata.d:(.text._ZN16CompleteAutomata4nextEv+0x2f): undefined reference to `_d_newclass' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o): In function `CompleteAutomata::save()': 
complete_automata.d:(.text._ZN16CompleteAutomata4saveEv+0x25): undefined reference to `_adDupT' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o): In function `CompleteAutomata::restore()': 
complete_automata.d:(.text._ZN16CompleteAutomata7restoreEv+0x33): undefined reference to `_d_newclass' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o): In function `CompleteAutomata::zerofile()': 
complete_automata.d:(.text._ZN16CompleteAutomata8zerofileEv+0x2f): undefined reference to `_d_newclass' 
/home/newmen/projects/d/life/lib/liblife.a(object_201_8b7.o): In function `no symbol': 
/usr/include/dmd/druntime/import/object.di:(.text+0x6): undefined reference to `_Dmodule_ref' 
/home/newmen/projects/d/life/lib/liblife.a(object_201_8b7.o):(.data._D12TypeInfo_Axi6__initZ+0x0): undefined reference to `_D14TypeInfo_Array6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(object_201_8b7.o): In function `_D46/usr/include/dmd/druntime/import/object.di.5137__arrayZ': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.5137__arrayZ+0x16): undefined reference to `_d_array_bounds' 
/home/newmen/projects/d/life/lib/liblife.a(object_201_8b7.o): In function `_D46/usr/include/dmd/druntime/import/object.di.5138__assertFiZv': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.5138__assertFiZv+0x16): undefined reference to `_d_assertm' 
/home/newmen/projects/d/life/lib/liblife.a(object_201_8b7.o): In function `_D46/usr/include/dmd/druntime/import/object.di.51315__unittest_failFiZv': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.51315__unittest_failFiZv+0x16): undefined reference to `_d_unittestm' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o): In function `no symbol': 
/usr/include/dmd/druntime/import/object.di:(.text+0x6): undefined reference to `_Dmodule_ref' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o):(.data._D11TypeInfo_xi6__initZ+0x0): undefined reference to `_D14TypeInfo_Const6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o):(.data._D11TypeInfo_xi6__initZ+0x10): undefined reference to `_D10TypeInfo_i6__initZ' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o): In function `_D46/usr/include/dmd/druntime/import/object.di.5157__arrayZ': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.5157__arrayZ+0x16): undefined reference to `_d_array_bounds' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o): In function `_D46/usr/include/dmd/druntime/import/object.di.5158__assertFiZv': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.5158__assertFiZv+0x16): undefined reference to `_d_assertm' 
/home/newmen/projects/d/life/lib/liblife.a(object_203_875.o): In function `_D46/usr/include/dmd/druntime/import/object.di.51515__unittest_failFiZv': 
/usr/include/dmd/druntime/import/object.di:(.text._D46/usr/include/dmd/druntime/import/object.di.51515__unittest_failFiZv+0x16): undefined reference to `_d_unittestm' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `no symbol': 
agregator.d:(.text+0x6): undefined reference to `_Dmodule_ref' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o):(.data+0x10): undefined reference to `_D3std6random12__ModuleInfoZ' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o):(.rodata+0x20): undefined reference to `_D14TypeInfo_Class6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D9agregator7__arrayZ': 
agregator.d:(.text._D9agregator7__arrayZ+0x16): undefined reference to `_d_array_bounds' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D9agregator8__assertFiZv': 
agregator.d:(.text._D9agregator8__assertFiZv+0x16): undefined reference to `_d_assertm' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D9agregator15__unittest_failFiZv': 
agregator.d:(.text._D9agregator15__unittest_failFiZv+0x16): undefined reference to `_d_unittestm' 
/home/newmen/projects/d/life/lib/liblife.a(agregator_2_5fd.o):(.data+0x0): undefined reference to `_D14TypeInfo_Class6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(agregator_2_5fd.o):(.data+0x50): undefined reference to `_D6Object7__ClassZ' 
/home/newmen/projects/d/life/lib/liblife.a(agregator_2_5fd.o):(.rodata+0x48): undefined reference to `_D6object6Object8toStringMFZAya' 
... 

W drugim przypadku (przy użyciu gdc) I otrzymuje wiadomość o«wielokrotnym definicji»:

g++ -Wl,-O1 -Wl,-z,relro -o cellular_life main.o mainwindow.o renderarea.o button.o playbutton.o moc_mainwindow.o moc_renderarea.o moc_button.o moc_playbutton.o -L/home/newmen/projects/d/life/lib -llife -lQtGui -lQtCore -lpthread 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `_D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi': 
complete_automata.d:(.text+0x0): multiple definition of `_D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::invert(unsigned long long, unsigned long long)': 
complete_automata.d:(.text+0x40): multiple definition of `CompleteAutomata::invert(unsigned long long, unsigned long long)' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZN16CompleteAutomata6invertEyy+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::state(unsigned long long, unsigned long long) const': 
complete_automata.d:(.text+0x60): multiple definition of `CompleteAutomata::state(unsigned long long, unsigned long long) const' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZNK16CompleteAutomata5stateEyy+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::x() const': 
complete_automata.d:(.text+0x80): multiple definition of `CompleteAutomata::x() const' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZNK16CompleteAutomata1xEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::y() const': 
complete_automata.d:(.text+0xa0): multiple definition of `CompleteAutomata::y() const' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZNK16CompleteAutomata1yEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::next()': 
complete_automata.d:(.text+0x140): multiple definition of `CompleteAutomata::next()' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZN16CompleteAutomata4nextEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.tbss+0x10): multiple definition of `_D17complete_automata16CompleteAutomata4nextMRZv7changerC7changer7Changer' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.tbss+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::restore()': 
complete_automata.d:(.text+0x1b0): multiple definition of `CompleteAutomata::restore()' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZN16CompleteAutomata7restoreEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.tbss+0x8): multiple definition of `_D17complete_automata16CompleteAutomata7restoreMRZv9agregatorC9agregator9Agregator' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.tbss+0x8): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.data+0x180): multiple definition of `_D_ZN16CompleteAutomata7restoreEv14SliceAgregator7__ClassZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::zerofile()': 
complete_automata.d:(.text+0x220): multiple definition of `CompleteAutomata::zerofile()' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZN16CompleteAutomata8zerofileEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.tbss+0x0): multiple definition of `_D17complete_automata16CompleteAutomata8zerofileMRZv9agregatorC9agregator9Agregator' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.tbss+0x10): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::save()': 
complete_automata.d:(.text+0x290): multiple definition of `CompleteAutomata::save()' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._ZN16CompleteAutomata4saveEv+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.data+0x80): multiple definition of `_D17complete_automata16CompleteAutomata7__ClassZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.data+0xd0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `_D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata': 
complete_automata.d:(.text+0x9b0): multiple definition of `_D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):complete_automata.d:(.text._D17complete_automata16CompleteAutomata6__ctorMFmmZC17complete_automata16CompleteAutomata+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.rodata+0x420): multiple definition of `_D17complete_automata16CompleteAutomata6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0xf0): first defined here 
/usr/bin/ld: Warning: size of symbol `_D17complete_automata16CompleteAutomata6__vtblZ' changed from 104 in /home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o) to 112 in /home/newmen/projects/d/life/lib/liblife.a(complete_automata.o) 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.rodata+0x4a0): multiple definition of `_D17complete_automata16CompleteAutomata6__initZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x90): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.rodata+0x4e0): multiple definition of `_D_ZN16CompleteAutomata7restoreEv14SliceAgregator6__vtblZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x60): first defined here 
/usr/bin/ld: Warning: size of symbol `_D_ZN16CompleteAutomata7restoreEv14SliceAgregator6__vtblZ' changed from 48 in /home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o) to 56 in /home/newmen/projects/d/life/lib/liblife.a(complete_automata.o) 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o):(.rodata+0x520): multiple definition of `_D_ZN16CompleteAutomata7restoreEv14SliceAgregator6__initZ' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1ff_675.o):(.rodata+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D3std7complex14__T7ComplexTeZ7Complex8toStringMxFMDFAxaZvAyaZAya12__lambda1223MFNbNfAxaZv': 
agregator.d:(.text+0xaf): undefined reference to `_D11TypeInfo_Aa6__initZ' 
agregator.d:(.text+0xb7): undefined reference to `_d_arrayappendT' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D3std4conv16__T6toImplTiTxkZ6toImplFNaNfxkZi15__dgliteral1389MFNaNfZC6object9Throwable': 
agregator.d:(.text+0xc5): undefined reference to `_D3std4conv21ConvOverflowException7__ClassZ' 
agregator.d:(.text+0xca): undefined reference to `_d_newclass' 
agregator.d:(.text+0xed): undefined reference to `_D3std4conv21ConvOverflowException6__ctorMFAyaAyamZC3std4conv21ConvOverflowException' 
/home/newmen/projects/d/life/lib/liblife.a(agregator.o): In function `_D3std6format17__T9getNthIntTxeZ9getNthIntFNaNfkxeZi.part.6': 
agregator.d:(.text+0x105): undefined reference to `_D3std6format15FormatException7__ClassZ' 
agregator.d:(.text+0x10a): undefined reference to `_d_newclass' 
... 

Po dwóch dniach prób, aby to zrobić ...

Ostatnio spróbowałem dodać Phobos (standardowa biblioteka D) do procesu łączenia. Dla flagi dmd -lphobos2 i dla flagi gdc -lgphobos2 odpowiadają. Ale to nie może mi pomóc ...

Podczas korzystania dmd wyjście łącznika:

g++ -Wl,-O1 -Wl,-z,relro -o cellular_life main.o mainwindow.o renderarea.o button.o playbutton.o moc_mainwindow.o moc_renderarea.o moc_button.o moc_playbutton.o -L/home/newmen/projects/d/life/lib -llife -lQtGui -lQtCore -lpthread -lphobos2 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `_Dmain' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
/usr/lib/gcc/x86_64-redhat-linux/4.7.2/../../../../lib64/libphobos2.so: undefined reference to `[email protected]_GNUTLS_3' 
collect2: error: ld returned 1 exit status 
make: *** [cellular_life] Error 1 

i mam spróbować namiastkę libCurl-GnuTLS: ln -s /usr/lib64/libcurl.so.4 /usr/lib64/libcurl-gnutls.so.4. Następnie wynik połączenia tego samego, ale bez wiadomości o libcurl-gnutls.

Podczas korzystania gdc wyjście łącznika znowu mówić o „wielokrotnym definicji na”:

/home/newmen/gcc/bin/g++ -Wl,-O1 -Wl,-z,relro -o cellular_life main.o mainwindow.o renderarea.o button.o playbutton.o moc_mainwindow.o moc_renderarea.o moc_button.o moc_playbutton.o -L/home/newmen/gcc/lib64 -L/home/newmen/projects/d/life/lib -llife -lQtGui -lQtCore -lpthread -lgphobos2 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `_D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi': 
complete_automata.d:(.text+0x0): multiple definition of `_D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1e3_675.o):complete_automata.d:(.text._D17complete_automata16CompleteAutomata7restoreMRZv14SliceAgregator9initValueMxFmmZi+0x0): first defined here 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata.o): In function `CompleteAutomata::invert(unsigned long long, unsigned long long)': 
complete_automata.d:(.text+0x40): multiple definition of `CompleteAutomata::invert(unsigned long long, unsigned long long)' 
/home/newmen/projects/d/life/lib/liblife.a(complete_automata_1e3_675.o):complete_automata.d:(.text._ZN16CompleteAutomata6invertEyy+0x0): first defined here 
... 
/home/newmen/gcc/lib64/libgphobos2.a(dmain2.o): In function `main': 
/home/newmen/projects/distrib/gcc-4.8.1/x86_64-unknown-linux-gnu/libphobos/libdruntime/../../.././libphobos/libdruntime/rt/dmain2.d:394: multiple definition of `main' 
main.o:/home/newmen/projects/d/life/qt_viewer/main.cpp:5: first defined here 
/usr/bin/ld: /home/newmen/gcc/lib64/libgphobos2.a(time.o): undefined reference to symbol '[email protected]@GLIBC_2.2.5' 
/usr/bin/ld: note: '[email protected]@GLIBC_2.2.5' is defined in DSO /lib64/librt.so.1 so try adding it to the linker command line 
/lib64/librt.so.1: could not read symbols: Invalid operation 
collect2: error: ld returned 1 exit status 
make: *** [cellular_life] Error 1 

z komunikatem o librt.so.1 na końcu. Sprawdzam/usr/lib64 i widziałem tam plik biblioteki.

Drodzy magicy, proszę, powiedz mi jak podłączyć bibliotekę D do kodu C++.

Odpowiedz

9

Jest generalnie łatwiej niech kompilator D zrobić łączenie:

g++ -c yourfile.cpp 
dmd yourfile.o d_file.d 

Być może trzeba dodać zawinięcie do niego, jak również, tak samo jak przedtem.Przekazać argument łącznika przez DMD (lub gdmd jeśli używasz GDC, powinny działać w ten sam sposób), przechodzą -Larg

dmd yourfile.o d_file.d -L-lstdc++ -L-lcurl -L-lQtGui # and so on 

Jest generalnie łatwiej umieścić main() D zbyt (to może tylko natychmiast wywołaj także funkcję zdefiniowaną w C++), ponieważ w przeciwnym razie prawdopodobnie będziesz musiał zainicjować środowisko wykonawcze D przed użyciem go z C++.

Ale aby zakończyć proces, który już zacząłeś ... pierwsza rzecz, wygląda na to, że twoja liblife.a ma ten sam plik dodany dwa razy. Próbowałbym usunąć ten plik i ponownie go utworzyć lub po prostu pominąć ten krok i przekazać pliki .o bezpośrednio do łącznika bez uprzedniego umieszczenia go w pliku .a. To trochę uprości sytuację.

Moje drugie pytanie brzmi: dlaczego próbuje wyciągnąć D-dur? Czy gdzieś znajduje się main() w twoim kodzie .d? Jeśli tak, to jest ok, ale będziesz musiał usunąć ten z twojego kodu C++. (Być może zmienić jego nazwę na cppmain a następnie wywołać ją z D głównej:

kodu D:

extern(C++) int cppmain(int argc, char** argv); 

int main() { 
     import core.runtime; 
     return cppmain(Runtime.cArgs.argc, Runtime.cArgs.argv); 
} 

I że przekaże do C++ Menem Jeśli chcesz usunąć D main (zakładając, że jest. tam, jeśli nie daj mi znać, a spróbuję zastanowić się, co jeszcze może spowodować ten błąd linkera), przed użyciem użyj kodu D w C++, musisz zainicjować D. Tak:

Kod D:

extern(C++) void initD() { 
     import core.runtime; 
     Runtime.initialize(); 
} 

C++ kod:

extern "C++" void initD(); 
int main() { 
     initD(); 
     // the rest of your stuff 
} 

Jeśli tego nie zrobisz, wywołanie funkcji D może spowodować uszkodzenie.

Podsumowując, jestem pewien, że masz duplikat pliku .o dodany do archiwum i główny zdefiniowany w D i C++. Usuń duplikat z archiwum i zabij jedną z duplikatów sieci, a powinieneś odnieść sukces.

+0

Zanim zobaczę twoją odpowiedź, dowiaduję się, że jako linker trzeba użyć 'dmd'. Próbowałem połączyć kod przy głównej funkcji opisanej w kodzie C++. W takim przypadku dostałem plik binarny, a po uruchomieniu dostałem segfault, który ostrzegasz. Teraz, po przeczytaniu twojego postu, próbowałem stworzyć główną funkcję w kodzie D i wywołać z niej funkcję cppmain, jak napisałeś. W takim przypadku, po połączeniu uzyskuję również plik binarny, który jest również wtedy, gdy zaczyna się uzyskiwać błąd segfault, ale tym razem jest on znacznie bardziej obfity i wskazuje, że wystąpił błąd w momencie odesłania do metod klasy D CompleteAutomata –

+0

Jednym z powszechnych błędów podczas wchodzenia do D z C++ jest to, że klasy D zawsze muszą być przydzielane sterty, więc upewnij się, że robisz: CompleteAutomata a = new CompleteAtomata() ;, a nie tylko CompleteAutomata a ;. Powodem jest, że klasy w D są zawsze wykonywane przez odwołanie (MyClass a in D jest najbardziej podobna do MyClass * a w C++), więc jeśli nie zainicjujesz go za pomocą nowego, referencja będzie miała wartość null i segfault, kiedy go użyjesz. –

+0

kolejna uwaga, klasy D powinny być nowymi z D, a klasy C++ powinny być zbudowane w C++. Istnieje sposób obejścia tego problemu, ale języki nie wiedzą, jak wywoływać konstruktory nawzajem, więc trzeba to zrobić ręcznie, aby zainicjować obiekt. O wiele łatwiej jest po prostu go w swoim ojczystym języku. –

Powiązane problemy