#1
  1. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    132
    Rep Power
    2

    Undefined reference to 'vtable for XXX'


    Hi.

    I have a question.

    consider the following code:

    Code:
    class A
    {
    protected:
    	virtual ~A();
    	virtual int get()=0;
    };
    
    
    class B: public A
    {
    private:
    	int b;
    protected:
    	virtual bool set(int m_b){b=m_b; return true;}
    };
    
    
    class C: public B
    {
    private:
    	int c;
    public:
    	C(int init=4):c(init){}
    	int get(){return c;}
    };
    
    
    int main()
    {
    	C num;
    	cout<<num.get();
    }
    when I try to compile it, I get this error:

    Building target: Testing
    Invoking: GCC C++ Linker
    g++ -o "Testing" ./main.o
    ./main.o: In function `A::A()':
    /home/XXX/workspace/Testing/Debug/../main.cpp:5: undefined reference to `vtable for A'
    ./main.o: In function `B::~B()':
    /home/XXX/workspace/Testing/Debug/../main.cpp:13: undefined reference to `A::~A()'
    ./main.o:(.rodata._ZTI1B[_ZTI1B]+0x8): undefined reference to `typeinfo for A'
    collect2: error: ld returned 1 exit status
    make: *** [Testing] Error 1

    what does it mean?

    BTW: when I set the destructor of A like this:


    Code:
    class A
    {
    protected:
    	virtual ~A(){} //fixes the problem
    	virtual int get()=0;
    };
    
    
    class B: public A
    {
    private:
    	int b;
    protected:
    	virtual bool set(int m_b){b=m_b; return true;}
    };
    
    
    class C: public B
    {
    private:
    	int c;
    public:
    	C(int init=4):c(init){}
    	int get(){return c;}
    };
    
    
    int main()
    {
    	C num;
    	cout<<num.get();
    }
    it fixes the problem.

    what doe's the vtable have to do with A's destructor?

    thanks in advanced!
    Last edited by so.very.tired; May 16th, 2013 at 06:02 AM.
  2. #2
  3. Contributing User

    Join Date
    Aug 2003
    Location
    UK
    Posts
    5,109
    Rep Power
    1803
    In class A you declared a virtual destructor, but did not define it. The reason you get this error rather than " undefined reference to ~A() " is explained here.
  4. #3
  5. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    132
    Rep Power
    2
    Hi, clifford. thanks for the help.

    Why must virtual methods be defined?
    I get that the compiler must have all the virtual functions in the vtable defined, my question is, why doesn't the compiler complain about undefined functions when they are not virtual?
    you might say that it is because there is no vtable, but what is so special about this vtable, that all the functions in it must be defined?

    BTW, that's merely curiosity.
    I don't really need to know that for my assignments...
  6. #4
  7. Contributing User

    Join Date
    Aug 2003
    Location
    UK
    Posts
    5,109
    Rep Power
    1803
    Originally Posted by so.very.tired
    Why must virtual methods be defined?
    In the case of a destructor - virtual or otherwise - the method must be defined because you declared it! Having declared it, the compiler will generate code to call it when an object is deleted or goes out of scope. If the compiler calls it, then obviously it has to exist.

    Originally Posted by so.very.tired
    my question is, why doesn't the compiler complain about undefined functions when they are not virtual?
    A virtual function is a "promise" to provide an interface - you promised, you provide. You can declare a pure virtual function without defining it - that is a promise that a sub-class will define an interface. You cannot instantiate an object with a pure virtual declaration; it is an abstract class - you have to sub-class it.

    Originally Posted by so.very.tired
    you might say that it is because there is no vtable, but what is so special about this vtable, that all the functions in it must be defined?
    A sub-class may call the virtual function without overriding it, so it has to exist because the base class promised it. Otherwise declare a pure virtual function, or remove the interface entirely.
  8. #5
  9. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Nov 2012
    Posts
    132
    Rep Power
    2
    Thanks for the great explanation.

IMN logo majestic logo threadwatch logo seochat tools logo