Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

gcc 4.5.1 virtual inheritance issue

Let's start from code snippet:

#include <iostream>

struct God{
    God(){_test = 8;}
    virtual ~God(){}
    int _test;
};

struct Base1 : public virtual God{
    //Base1(){std::cout << "Base1::Base1" << std::endl;}  //enable this line to fix problem
    virtual ~Base1(){}
};

struct Base2 : public virtual Base1{
    virtual ~Base2(){}
};

struct A1 : public virtual Base2{
    A1(){std::cout << "A1:A1()" << std::endl;}
    virtual ~A1(){};
};

struct A2 : public virtual Base2{
    A2(){std::cout << "A2:A2()" << std::endl;}
    virtual ~A2(){};
};


struct Derived: public virtual A1, public virtual A2{
    Derived():Base1(){std::cout << "Derived::Derived()" << std::endl;}
    Derived(int i){std::cout << "Derived(i)::Derived(i)" << std::endl;}         
    virtual ~Derived(){}
};


int main(){

    God* b1 = new Derived();
    std::cout << b1->_test << std::endl;    //why it prints 0?

    God* b2 = new Derived(5);
    std::cout << b2->_test << std::endl;

    return 0;
}

Compiled with GCC 4.5.1 and 4.6.1 The only difference between constructors of Derived class is that first one explicitly states which Base1 constructor should be called. I would expect that both cout in main() print 8. Unfortunately the first one prints 0!.

Why?

If I enable explicit definition of Base1 constructor it fixes the problem. If I remove virtual inheritance in Derived class definition (class Derived: public A1, public A2) it works as well. Is it expected behaviour?

The issue is not observable under GCC 3.4.4 or Microsoft compiler (VS)

like image 225
Kamil_H Avatar asked Feb 08 '12 23:02

Kamil_H


1 Answers

This must be a compiler bug. I also tested GCC 4.2.1 and the result is 8 both cases.

like image 178
rasmus Avatar answered Sep 28 '22 00:09

rasmus