1

OK, I have been looking about but can not for the wits of me find a reason to why this should not work:

Base class (misc/interface/handler.h)

#ifndef __t__MISC_VIRTUAL_HANDLER_H
#define __t__MISC_VIRTUAL_HANDLER_H
#pragma message("Starting with 'handler.h'")

namespace t {
    namespace misc {
        namespace interface {
            class Handler {
                public:
                    Handler();
                    virtual ~Handler();

                    virtual int setup() = 0;
                    virtual int teardown() = 0;
                    virtual int update() = 0;
                protected:
                private:
            };
        }
    }
}

#pragma message("Ending with 'handler.h'")
#endif // __t__MISC_VIRTUAL_HANDLER_H

Derived class (graphics/handler.h):

#ifndef __t_GRAPHICS_HANDLER_H
#define __t_GRAPHICS_HANDLER_H

#include "../misc/interface/handler.h"

namespace t {
    namespace graphics {
        class Handler: public t::misc::interface::Handler {
            public:
                Handler();
                virtual ~Handler();

                int getResolutionX() { return m_resolutionX; }
                int getResolutionY() { return m_resolutionY; }
                bool getFullscreen() { return m_isFullscreen; }

            protected:
            private:
                unsigned int m_resolutionX, m_resolutionY;
                bool m_isFullscreen;

        }; // class Handler
    } // namespace graphics
} // namespace t
#endif // __t_GRAPHICS_HANDLER_H

... which seems rather trivial.

Derived class implementation (graphics/handler.cpp):

#include "handler.h"

t::graphics::Handler::Handler(): t::misc::interface::Handler() {

}

t::graphics::Handler::~Handler() {
}

... which too is should be really trivial, but yields the error:

src\graphics\handler.cpp|5|undefined reference to `t::misc::interface::Handler::Handler()'

I'm using MinGW with Code Blocks and what ever standard settings CB uses, I've tried building the same situation with test classes and that works as intended, both in same environment and Linux with vanilla g++.

JDW
  • 175
  • 3
  • 12
  • 1
    Try removing the namespaces and look if the problem can be reproduced. Put the files into the same directory and do the same: If the pragmas are not printed, the file isn’t included, or the include guard is already defined. Period. Always strive to produce a *minmal* code that reproduces the problem. – Konrad Rudolph Nov 12 '10 at 13:51
  • 1
    Agreed with @Konrad. In fact you'll find that simply by preparing your question for SO, you'll solve your problem many times. – John Dibling Nov 12 '10 at 14:05

2 Answers2

5

I can't see any implementation of t::misc::interface::Handler::Handler() in your code - and it is going to be called by the inheriting class's constructor, so it needs an implementation. The linker can't find it, so it complains.

Just change:

Handler();
virtual ~Handler();

in the abstract class to:

Handler() {}
virtual ~Handler() {}

and you're ready to go.

Kos
  • 70,399
  • 25
  • 169
  • 233
3

As an aside, identifiers starting with two underscores are illegal in C++ (since they are reserved for the compiler). In practice, they shouldn’t be a problem in preprocessor but it’s best to err on the safe side here: simply don’t use them.

Konrad Rudolph
  • 530,221
  • 131
  • 937
  • 1,214
  • Fixed. (but shouldnt the compiler complain?) – JDW Nov 12 '10 at 14:08
  • @JDW: Nope. Basically the compiler just gets first pick. It *can* define any name in that category, but if it doesn't, there's really nothing to stop you from defining the name yourself. But if there ends up being a conflict, it's *your fault*, because you used a reserved name. They're not forbidden, just dangerous. (The full set of reserved names are: any name *containing* a double underscore, any name starting with underscore followed by upper-case letter, and any name starting with underscore at namespace scope (that is, not inside a function or class) – jalf Nov 12 '10 at 14:17
  • think of it as running out onto the highway. No one's stopping you from doing it, and you can get away with it as long as you pay attention (and are lucky), but there's a chance of getting hit by a truck, and if you do, it's really your own fault. So it's safer to just keep away. – jalf Nov 12 '10 at 14:21