Sziasztok!
Adva van egy MSVC-vel (8.0) fordított dll, a hozzá való .lib, és .h fájlokkkal. Ezt szeretném használni egy mingw-s programból.Ez alapján csináltam .a fájlt.
Ha a .h fájlokban az osztályoknál van __declspec(dllimport), akkor ilyeneket kapok:
surfdetector.cpp:53: undefined reference to `_imp___ZN4surf5ImageC1EPS0_b'
Ha nincs, akkor ilyeneket:
surfdetector.cpp:53: undefined reference to `surf::Image::Image(surf::Image*, bool)'
A dll-ben ilyen tuti van (méghozzá __thiscall előtaggal, bármi is ez)...
Ötlet?
- 3432 megtekintés
Hozzászólások
A "surfdetector.cpp:53: undefined reference to ..." üzenet azt jelenti, hogy a .cpp 53. sorában hivatkozol valamire, amihez nincs definíció, vagyis itt még nem jutott el odáig, hogy a .dll-t vizsgálná.
A hibát a .h fájlban keresd!
- A hozzászóláshoz be kell jelentkezni
"undefined reference is a linker error. It's not a compile error. #includes don't help. You did not define the thing in the error message, or you forgot to link the file that defines it, or you forgot to link to the library that defines it, or if its a static library you have the wrong order. Check which one. (Note that on some compilers it's called unresolved external)"
- A hozzászóláshoz be kell jelentkezni
1500%, hogy linkelési időben történik...
Illetve az is biztos, hogy -lakarmi is ott van és libakarmi.a fájl is van, és meg is találja.
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Akkor az lesz a probléma, hogy a C++ fordító a neveket a függvény tipusától függően kiegészíti, és a kiegészítés szabályai az MSVC és a MINGW esetén eltérnek.
A megoldás az lehet, hogy megnézed a tényleges függvény neveket a könyvtárakban és futásidőben töltöd be a dll-t (LoadLibrary) és a függvényeket(GetProcAddress).
- A hozzászóláshoz be kell jelentkezni
Ezzel az a gond, hogy ez egy C++-os lib, és nincs felkészítve ilyen használatra, tehát nincs factrory fv...
Azaz egyenként kéne a tagfv-ek címeit lekérnem, beállítanom, ami macerás, illetve most hirtelen nem is látom, hogy a konstruktorok esetében ez működne-e...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
"Akkor az lesz a probléma, hogy a C++ fordító a neveket a függvény tipusától függően kiegészíti, és a kiegészítés szabályai az MSVC és a MINGW esetén eltérnek."
Reméltem, hogy csak ez a külömbség, és ez valami ügyes tool-lal megoldható. A mingw faq is erre engedett következtetni.
Most viszont ott tartok, hogy a .def fájlban kézzel felvettem a mingw által keresett neveket mint aliast. Ebből .a fájlt generálva a program lefordult, majd azonnal elhalt... Valószínűleg komolyabb különbség van.
Gyanum szerint a gondot a thiscall hívás okozza, és nekem úgy tűnik, mingw alatt nincs lehetőség a msvc-féle működésre...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
up
- A hozzászóláshoz be kell jelentkezni
Pontosan milyen fordítási parancsot is használsz?
Használod-e a -L... kapcsolót a lib elérhetőségének megadására?
- A hozzászóláshoz be kell jelentkezni
surfWINDLL.dll a dll neve, használom a -L-t a könyvtármegadáshoz, illetveilletve -lsurfWINDLL-t a lib-hez.
A libet megtalálja, ha hülyeséget írok, rögtön sikít...
Elméletileg a MinGW -lakarmi esetén először libakarmi.a-t keres, majd akarmi.dll, tehát ez se lehet gond...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Elméletileg a MinGW -lakarmi esetén először libakarmi.a-t keres, majd akarmi.dll, tehát ez se lehet gond...
Ez nem MinGW specialitas, hanem W32 okorseg. DLL-t direktbe nem lehet linkelni, kell hozza egy imp lib, hogy tudja a linker mit kell osszecuccolni. Ezt az export file-bol a dllwrap/dlltool parossal lehet generalni. Az export file-t pedig nm-bol egy perl scriptel. Ez megtalalhato a mingw.org-on (is).
---
pontscho / fresh!mindworkz
- A hozzászóláshoz be kell jelentkezni
Valójában de: lásd itt
"direct linking to a dll" részben
"Linking directly to a dll without using the import library can be done two ways:"
Egyébként nyilván ez se csinál mást, mint a scriptes, dlltool-os megoldás.
De ha elolvasod a topic többi résztét rájössz, hogy messze nem itt a gond...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Jah, lattam, csak nem egeszseges az a feature. Viszont a dll az "sajat" cucc, vagy egyaltalan nincs lehetoseg egy-ket modositast kerni?
---
pontscho / fresh!mindworkz
- A hozzászóláshoz be kell jelentkezni
Nem, nem saját, és nem lehet módosítást kérni.
Az ő nézőpontjukból mindent megtettek, hiszen van msvc 7-es, msvc 8-as verzió is, sőt van egy Linuxos gcc-s.
Az már az én hülyeségem, hogy win alatt mingw-vel akarom használni... :)
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
>> DLL-t direktbe nem lehet linkelni, kell hozza egy imp lib, hogy tudja a linker mit kell osszecuccolni.
nem
- A hozzászóláshoz be kell jelentkezni
ok
---
pontscho / fresh!mindworkz
- A hozzászóláshoz be kell jelentkezni
Köszi mindenkinek, a probléma megoldhatalan, legalábbis így.
A c++ elnevezések kódolása még véletlenül sem egyforma, ugyanis nincs ilyen a szabványban. Hasonlóan a hívási módok is különböznek.
Win alatt van szabvány (COM) amivel virtuális osztályok esetében megoldható, de ott sem egyszerű, eleve úgy kell tervezni az osztályt.
Esetemben csak az működne, ha Visual C++-ban írnék egy wrapper dll-t, ami vagy tisztán C fv-ekkel, vagy COM-on keresztül csatlakozik a külvilághoz. Természetesen se kivétel, se STL, sőt a structokkal is vigyázni kell...
Inkább hagyom az egészet...
Ha valakit érdekel részletesebben:
http://aegisknight.org/cppinterface.html
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Kedves tr3w.
Ajanlom az extern "C" {} kiprobalasat, a Stroustup (??) konyvbe is ez az ajanlas (ha jol emlexem).
Pl.:
#ifdef __cplusplus
extern "C" {
#endif
void doSomeThing(string stuff);
#ifdef __cplusplus
}
#endif
Vagy
extern "C" void doSomeThing(string stuff);
Az extern "C" ugyanis azt jelenti, hogy C stilusu fuggvenynev generalast szeretnel.
Ketto dolog nem megengedett:
- classokon beluli fuggvenyek extern -elese
- overloadolt fuggvenyek 1-nel tobb valtozatanak extern-elese.
- A hozzászóláshoz be kell jelentkezni
illetve void doSomeThing előtt __declspec(dll*) __stdcall/más linkagetype
- A hozzászóláshoz be kell jelentkezni
Látom write only. :)
Tehát mint írtam, a dll-t amit használni szeretnék, nem én írtam, tehát nem tudom módosítani, sem hogy extern "C"-vel, sem még __stdcall-lal.
A dll-ben pár teljesen közönséges class van, olyan formában, ahogy az msvc kiköpi, ha kap egy __dllspec(dllexport)-ot.
Írhatnék köré egy C-s wrappert, de ez most elmarad...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Szia, ha még aktuális.
MSVC lib-et nem tudsz megetetni gcc-vel csak MS cl-el. Szerintem. Nekem nem jött össze.
Én azt csináltam, hogy LoadLibrary-val betöltöttem a dll-t, így nem kell sem .lib sem .h.
Mondjuk én tudtam, hogy mi van a dll-ben, de ez számodra is kiderül a .h-ból.
Szóval így kaptam egy handle-t a dll-re azt egy GetProcAddress(kapott_handle, "Függvény neve a .h szerint");
visszaadott egy pointer-t, amit ha a megfelelő függvény pointer kapott meg, akkor már meg
is tudtam hívni, és működik a mai napig.
Szerintem.
--
"Megtanultam a zenét, de nem csináltam, s azóta tudással, de irigység nélkül hallgatom.
Megtanultam egy sereg tudományt, mesterséget és művészetet, értek hozzájuk, de nem csinálom, s így érdektelenül tudom azokat élvezni. "
Hamvas Béla
- A hozzászóláshoz be kell jelentkezni
Meg tudja etetni, van valami konverzio a .lib - .a iranyra. Ra kell keresni, mar en sem emlexem.
--
()=() Ki oda vagyik,
('Y') hol szall a galamb
C . C elszalasztja a
()_() kincset itt alant.
- A hozzászóláshoz be kell jelentkezni
A dll, és a lib C++, ezért a normál konverzió nem ér semmit. (Felesleges is, mert a mingw megeszi a C-s .lib-et gond nélkül.)
Elméletileg lehetne írni olyan konvertálót, ami egy rövid kódot a hívás elé rak, és megoldja az eltérő paraméterátadást, stb-t, de ilyen nem létezik.
(Mondjuk a kivételkezelés, meg az stl-es paraméterek átadása, plusz egy csomó minden nem működne, így nem sok értelme lenne egy ilyennek...)
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
GetProcAddress nem jó, mert ez egy C++-os lib...
Mindenféle .def fileokkal lehet trükközni, de szart se ér, mert a gcc-nél és az msvc-nél c++ esetében még a paraméterátadási konvenciók sem egyeznek...
Úgyhogy bukta...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni
Hát nem biztos, hogy ez értelmes lesz itt, de sebaj.
http://gcc.gnu.org/onlinedocs/gcc-4.4.0/gcc/Interoperation.html
On many platforms, GCC supports a different ABI for C++ than do other compilers, so the object files compiled by GCC cannot be used with object files generated by another C++ compiler.
An area where the difference is most apparent is name mangling. The use of different name mangling is intentional, to protect you from more subtle problems. Compilers differ as to many internal details of C++ implementation, including: how class instances are laid out, how multiple inheritance is implemented, and how virtual function calls are handled. If the name encoding were made the same, your programs would link against libraries provided from other compilers—but the programs would then crash when run. Incompatible libraries are then detected at link time, rather than at run time.
- A hozzászóláshoz be kell jelentkezni
Igen pont ez volt a probléma...
"...handing C++ to the average programmer seems roughly comparable to handing a loaded .45 to a chimpanzee."
-- Ted Ts'o
- A hozzászóláshoz be kell jelentkezni