Important: Please read the Qt Code of Conduct -

[SOLVED] Problem Linking after changing project to dynamic rather than static.

  • I am pretty new to Qt.
    I am using Qt and the Qt plugin for Visual Studio 2010. I am creating a multi-library project that involves plugins and interfaces. While solving an earlier problem I temporarily set one of the dll projects (BuilderCore) to build a static library. I got it to build fine but I noticed I was missing one of the dlls in the Win32 Debug folder. I realized that I was still doing a static library build for that particular project. So I changed it back to the dll version.

    As soon as I changed it back I got 7 linking errors. I have tried all the "removing Q_OBJECT" as many LNK2019 and LNK2001 articles have suggested and then adding back. I have tried compiling with and without the Q_OBJECT in the derived class without success.

    Some possibly important information. The IBuilderRole "interface" class is located in the BuilderCore dll (that was originally statically linked when it worked). It is derived from QObject and a basic ground level BuilderObject class that defines all classes that need specific object information stored for use in scripting and events that will occur within the application. The BuilderClient class is derived from the IBuilderRole interface and is in its own separate dll. All functions listed have been implemented in a cpp file.

    Here is the IBuilderRole header:
    namespace BuilderCore

    class IBuilderRole : public QObject, BuilderObject

    IBuilderRole(const char* derivedRoleName, int roleID);
    virtual ~IBuilderRole();
    QList<IBuilderMode*>& GetModes() const;
    QList<QAction*>& GetActions() const;
    BuilderRoles GetRole() const;

    void RoleAdded(); // triggered when Role has been initialized
    void RoleReady(); // triggered when Role is ready to begin
    void RoleStarted(); // triggered when Role has first started
    void RoleBeginRemove(); // triggered when Role needs to end
    void RoleEndRemove(); // triggered when Role has ended
    void RoleCleared(); // triggered just before dynamic library is unloaded

    virtual void AddRole() = 0;
    virtual void SetupRole() = 0;
    virtual void Start() = 0;
    virtual void Stop() = 0;
    virtual void ShutdownRole() = 0;
    virtual void RemoveRole() = 0;

    QList<IBuilderMode*>& mModes;
    QList<QAction*>& mActions;
    BuilderRoles mRole;


    Q_DECLARE_INTERFACE(BuilderCore::IBuilderRole, "BuilderRoleInterface/1.0")

    Here is the BuilderClient class header. Note that I have experimented with the Q_OBJECT line with and without the comment marks. Without the comment line it it says "undefined interface" in reference to the Q_INTERFACES line. Adding the BuilderCore:: namespace in front of IBuilderRole in this line gets rid of that error but goes back to the problem with linking.
    namespace BuilderCore

    class BUILDERCLIENT_EXPORT BuilderClient : public IBuilderRole


    virtual void AddRole();
    virtual void SetupRole();
    virtual void Start();
    virtual void Stop();
    virtual void ShutdownRole();
    virtual void RemoveRole();

    // Nothing yet...


    Here are the link errors I am getting:
    3> Creating library D:\Developing\Projects\IMT\Rosweld\trunk\Source\Builder\Win32\Debug\BuilderClient.lib and object D:\Developing\Projects\IMT\Rosweld\trunk\Source\Builder\Win32\Debug\BuilderClient.exp
    3>builderclient.obj : error LNK2019: unresolved external symbol "public: __thiscall BuilderCore::IBuilderRole::IBuilderRole(char const *,int)" (??0IBuilderRole@BuilderCore@@QAE@PBDH@Z) referenced in function "public: __thiscall BuilderCore::BuilderClient::BuilderClient(void)" (??0BuilderClient@BuilderCore@@QAE@XZ)
    3>builderclient.obj : error LNK2001: unresolved external symbol "public: virtual struct QMetaObject const * __thiscall BuilderCore::IBuilderRole::metaObject(void)const " (?metaObject@IBuilderRole@BuilderCore@@UBEPBUQMetaObject@@XZ)
    3>builderclient.obj : error LNK2001: unresolved external symbol "public: virtual void * __thiscall BuilderCore::IBuilderRole::qt_metacast(char const *)" (?qt_metacast@IBuilderRole@BuilderCore@@UAEPAXPBD@Z)
    3>builderclient.obj : error LNK2001: unresolved external symbol "public: virtual int __thiscall BuilderCore::IBuilderRole::qt_metacall(enum QMetaObject::Call,int,void * *)" (?qt_metacall@IBuilderRole@BuilderCore@@UAEHW4Call@QMetaObject@@HPAPAX@Z)
    3>builderclient.obj : error LNK2019: unresolved external symbol "public: virtual __thiscall BuilderCore::IBuilderRole::~IBuilderRole(void)" (??1IBuilderRole@BuilderCore@@UAE@XZ) referenced in function "public: virtual __thiscall BuilderCore::BuilderClient::~BuilderClient(void)" (??1BuilderClient@BuilderCore@@UAE@XZ)
    3>builderclient.obj : error LNK2019: unresolved external symbol "public: void __thiscall BuilderCore::IBuilderRole::RoleAdded(void)" (?RoleAdded@IBuilderRole@BuilderCore@@QAEXXZ) referenced in function "public: virtual void __thiscall BuilderCore::BuilderClient::AddRole(void)" (?AddRole@BuilderClient@BuilderCore@@UAEXXZ)
    3>D:\Developing\Projects\IMT\Rosweld\trunk\Source\Builder\Win32\Debug\BuilderClient.dll : fatal error LNK1120: 6 unresolved externals

    The only thing I can think of (but I don't know how to do) is that perhaps the moc files for the BuilderCore class would be needed for the derived builderclient class as well?

  • UMMM... DUH... I cannot believe I overlooked the missing Export tag... I only noticed it after posting this and looking at the two together. Anyway... this is the only post I have found on the internet that talks about this kind of problem occuring only after switching from static to dynamic so I guess I will just leave it up. Maybe someone else will benefit from this ridiculous error on my part.

    So here is the solution: I forgot to declare the class an export by using the QT define generated when the project first gets made. The class line of the first file (Interface) should read:

    class BUILDERCORE_EXPORT IBuilderMode : QObject, BuilderObject

  • How do I mark this as answered?

  • Hi primem0ver.
    Thank you for sharing solution.
    You can edit first post and prepend [Solved] to caption.

Log in to reply