I have two files: RollDice.cpp
#include "RollDice.h"
#include "./IPlugins.cpp"
#include "./IPluginFunctions.cpp"
#include <iostream>
RollDice::RollDice(IPluginFunctions &iPluginFunctions) :
IPlugins(iPluginFunctions) {
//srand(time(NULL));
}
RollDice::~RollDice() {
}
void RollDice::callPlugin(std::string paramsText, std::string dataText) {
std::cout << "RollDice ;)\n";
}
RollDice.h:
#ifndef ROLLDICE_H_
#define ROLLDICE_H_
#include "./IPlugins.h"
#include "./IPluginFunctions.h"
class RollDice: public IPlugins {
public:
RollDice(IPluginFunctions &iPluginFunctions);
virtual ~RollDice();
virtual void callPlugin(std::string paramsText, std::string dataText);
};
extern "C" RollDice* create(IPluginFunctions &iPluginFunctions) {
return new RollDice(iPluginFunctions);
}
extern "C" void destroy(RollDice *rollDice) {
delete rollDice;
}
#endif /* ROLLDICE_H_ */
I create .so file with: g++ -shared -o RollDice.so RollDice.cpp
And now in my application I want to open this plugin:
this->plugin = dlopen(directory.c_str(), RTLD_LAZY);
if (!(this->plugin)) {
std::cerr << "Cannot load library: " << dlerror() << '\n';
return;
}
dlerror();
this->createPlugin = (create_p*) dlsym(plugin, "create");
const char* dlsymError = dlerror();
if (dlsymError) {
std::cerr << "Cannot load symbol create: " << dlsymError << '\n';
return;
}
this->destroyPlugin = (destroy_p*) dlsym(plugin, "destroy");
dlsymError = dlerror();
if (dlsymError) {
std::cerr << "Cannot load symbol destroy: " << dlsymError << '\n';
return;
}
But I get message: Cannot load library: ./RollDice.so: invalid ELF header
Can you help me solving this?
-fPIC
doesn't help
Edit:
Now I'm bulding plugin with:
g++ -shared -fPIC -o RollDice.so RollDice.h IPlugins.cpp IPluginFunctions.cpp
and I have new problem: Cannot load symbol create: ./RollDice.so: undefined symbol: create
When I use nm
to see what symbols are in RollDice.so I don't see "create"
One thing to check that doesn't seem to have been mentioned yet is that the exact name 'create' must be exported from your shared library.
Try
nm --dynamic --defined-only RollDice.so | grep create
If you get no matches, or get some mangled symbol for 'create', then your dlsym(..., "create") call is bound to fail.
Also, once you solve the name lookup issues, you should seriously consider adding RTLD_GLOBAL to your dlopen flags. dlopen defaults to RTLD_LOCAL, which interacts poorly with C++ shared libraries w.r.t. RTTI, exceptions, typeinfo, etc. RTLD_GLOBAL will lead to fewer surprises.
Also consider using RTLD_NOW rather than RTLD_LAZY. If there are symbols in your plugin library that were not resolvable at dlopen time, you have just created a ticking time bomb. Better to know at dlopen time whether the library was able to satisfy all of the required references or not.
edit:
I overlooked that checking for 'create' with 'nm' had already been suggested. However the dlopen flags advice is still important.
Also, your compilation line looks very odd to me, especially that you are including the RollDice.h on the build line, rather than the RollDice.cpp file.
In addition, including .cpp files in other .cpp files is not standard practice.
I'd suggest eliminating the .cpp to .cpp inclusion, and then compiling the various .cpp files separately with -o, then merging them into a shared library:
g++ -g -fPIC -c -o RollDice.o RollDice.cpp
g++ -g -fPIC -c -o IPluginFunctions.o IPluginFunctions.cpp
g++ -g -fPIC -c -o IPlugins.o IPlugins.cpp
g++ -g -fPIC -shared -o RollDice.so RollDice.o IPluginFunctions.o IPlugins.o
You didn't build your shared lib using -fPIC to produce position independent code, which IIRC is required by shared libraries.
A quick google reinforces my hunch: http://www.fpx.de/fp/Software/tcl-c++/tcl-c++.html
So use:
g++ -shared -fPIC -o RollDice.so RollDice.cpp
And see if that helps.
The other thing that causes errors of that sort are when you are trying to use libraries built for different architectures (eg ARM, 32, 64, etc), but I am assuming you aren't building the plugin .so in a different environment to the one which you are compiling the core program.
来源:https://stackoverflow.com/questions/6305554/c-dynamic-library-dlopen-error