title: C++: Undefined symbols when loading shared library with dlopen()
body: <p>I have an issue when I try to use dlopen() to load a shared library into another shared library. I checked all tutorials on how to use dlopen() correctly. So here is the simplified code:</p>
  
  <p>The main shared library contains a class with pure virtual functions which the sub-shared library (aka plug-in) must implement. Additionally, it has some other functions which are implemented with a default behavior. I created a macro which is added to every plug-in to have a symbol to load and create the class.</p>
  
  <p><strong>Main shared library</strong></p>
  
  <p><strong>plugin.h:</strong></p>
  
  <pre><code>Class A {
  public:
    virtual int func1() = 0;
    virtual bool func2() const;
  }
  
  #define CREATE_CLASS(cls) extern "C" void *CreateClass(void) { return new cls; }
  </code></pre>
  
  <p><strong>plugin.cpp:</strong></p>
  
  <pre><code>bool A::func2() const {   return true; }
  </code></pre>
  
  <p><strong>Build and link main.so</strong></p>
  
  <pre><code>g++ -g -Wall -Woverloaded-virtual -Wno-parentheses -O2 -fPIC -c -o plugin.o plugin.cpp
  g++ -g -Wall -Woverloaded-virtual -Wno-parentheses -O2 -fPIC  -rdynamic -shared plugin.o -ldl -o main-plugin.so
  </code></pre>
  
  <p>The sub-shared library does only implement the pure-virtual functions. The other function can be overridden though it is optional.</p>
  
  <p><strong>Sub shared library</strong></p>
  
  <p><strong>plugin-impl.cpp</strong></p>
  
  <pre><code>Class B : public A {
  public:
    virtual int func1() { return 0; }
  }
  
  CREATE_CLASS(B)
  </code></pre>
  
  <p>These are the lines to build and link the sub-shared library.</p>
  
  <p><strong>Build and link sub.so</strong></p>
  
  <pre><code>g++ -g -O3 -Wall -Werror=overloaded-virtual -Wno-parentheses -fPIC -c -o subPlugin.o subPlugin.cpp
  g++ -g -O3 -Wall -Werror=overloaded-virtual -Wno-parentheses -fPIC  -shared subPlugin.o  -o subPlugin.so
  </code></pre>
  
  <p>This is the line to open the sub-shared library. I tried LAZY, NOW, NOW | GLOBAL and so on, without any effects.</p>
  
  <p><strong>dlopen() call somewhere in the main-shared library:</strong></p>
  
  <pre><code>  handle = dlopen(file.c_str(), RTLD_LAZY);
  </code></pre>
  
  <p>Most of this is working very well. However, when I try to load the sub-shared library into the main shared library, dlopen complains about the undefined symbol of <code>bool A::func2() const</code>. The function does only exists in the main shared library, so I guess it must be exported anyway. Please help me out! I am very confused!</p>
  
  <h1><strong>SOLUTION</strong></h1>
  
  <p>Because I cannot change the executable, I have to link the main-shared library with the sub-shared librarys by adding the following options to g++:</p>
  
  <pre><code>-L$(PLUGINDIR) -Wl,-R$(PLUGINDIR) -lmain-shared
  </code></pre>
  
  <p>With this set, it is not required to set the <code>LD_LIBRARY_PATH</code>.</p>