tags:

views:

366

answers:

2

Hi there

I am writing a library, which is dynamically loaded in my main-application with dlsym. I have the following files:

library.h

#include <ilibrary.h>
#include <igateway.h>

class LibraryImpl;

class Library: public ILibrary {
public:
    static ILibrary* instance();

    IGateway* getGateway() const;

protected:
    Library();
    virtual ~Library();

private:
    static ILibrary* instance_;
    LibraryImpl* library_;
};

extern "C" {
    IMPORT_EXPORT ILibrary* getLibrary();
}

library.cpp

#include "library.h"

#include "business/BCGateway.h"


class LibraryImpl {
public:
    IGateway* getGateway();
};

IGateway* LibraryImpl::getGateway() {
    return BCGateway::instance();
}



ILibrary* Library::instance_ = NULL;
ILibrary* Library::instance() {
    return instance_ ? instance_ : (instance_ = new Library);
}

Library::Library() {
    library_ = new LibraryImpl();
}

Library::~Library() {
    delete library_;
}

IGateway* Library::getGateway() const {
    return library_->getGateway();
}


extern "C" {
    IMPORT_EXPORT
    ILibrary* getLibrary(){
        return Library::instance();
    }
}

business/BCGateway.h

#include <igateway.h>

class BCGateway: public IGateway {
public:
    static IGateway* instance();

protected:
    BCGateway();

private:
    static IGateway* instance_;
};

business/BCGateway.cpp

#include "BCGateway.h"

IGateway* BCGateway::instance_ = NULL;
IGateway* BCGateway::instance(){
    return instance_ ? instance_ : (instance_ = new BCGateway);
}

I can connect to the library and successfully load the Library-instance. But when I call library->getGateway() in my main-app I get the following error:

symbol lookup error: ./gateways/libSwisscomXtraZone.so: undefined symbol: _ZN9BCGateway8instanceEv

Can you please give me a hint, how I can resolve this? I'm stuck.

Thanks.

A: 

well all static members must be intialised in a cpp file. Seeing as BCGateway::instance is not intialised at any point it will be unable to find the symbol. The problem is, however, that if you create a BCGateway.cpp and initialise the instance then you will end up only having one instance across, potentially, many processes. This may or may not be a problem depending on how you use the DLL.

Goz
Instances will not be shared across processes. Not even in a shared library.
Jonathan Leffler
All symbols need to be 'defined'. This one is only 'declared'. I guess that's what you mean to say. (As opposed to 'initialized')
xtofl
Cheers xtofl. You are quite right :)
Goz
well, I just did not add the content of BCGateway.cpp above. I have it in my library. I edited my first post and inserted the missing BCGateway.cpp
Sämy
+4  A: 

I put the error through c++filt, it says that the mangled name stands for

BCGateway::instance()

This suggests that you call BCGateway::instance() somewhere and forgot to link against BCGateway.o or you even forgot to define BCGateway::instance().

Johannes Schaub - litb
Written my last comment, I saw, that I just have forgotten to add the BCGateway.h and BCGateway.cpp to my project file, out of which the makefile is generated. So this class was indeed not declared in my library. Since I am very new to c++ libraries, I thought it is an issue with the library declaration or so. Thanks a lot for your help.
Sämy