Situation is following. I have shared library, which contains class definition –
QueueClass : IClassInterface
{
virtual void LOL() { do some magic}
}
My shared library initialize class member
QueueClass *globalMember = new QueueClass();
My share library export C function which returns pointer to globalMember –
void * getGlobalMember(void) { return globalMember;}
My application uses globalMember like this
((IClassInterface*)getGlobalMember())->LOL();
Now the very uber stuff – if i do not reference LOL from shared library, then LOL is not linked in and calling it from application raises exception. Reason – VTABLE contains nul in place of pointer to LOL() function.
When I move LOL() definition from .h file to .cpp, suddenly it appears in VTABLE and everything works just great.
What explains this behavior?! (gcc compiler + ARM architecture_)
The linker is the culprit here. When a function is inline it has multiple definitions, one in each cpp file where it is referenced. If your code never references the function it is never generated.
However, the
vtablelayout is determined at compile time with the class definition. The compiler can easily tell that theLOL()is a virtual function and needs to have an entry in thevtable.When it gets to link time for the app it tries to fill in all the values of the
QueueClass::_VTABLEbut doesn’t find a definition ofLOL()and leaves it blank(null).The solution is to reference
LOL()in a file in the shared library. Something as simple as&QueueClass::LOL;. You may need to assign it to a throw away variable to get the compiler to stop complaining about statements with no effect.