Search code examples
c++visual-studio-2008friendvirtual-inheritancedefault-copy-constructor

MSVC9.0 bug or misunderstanding of virtual inheritance and friends?


consider the following code:

class A
{
    friend class B;
    friend class C;
};

class B: virtual private A
{
};

class C: private B
{
};

int main()
{
    C x; //OK default constructor generated by compiler
    C y = x; //compiler error: copy-constructor unavailable in C
    y = x; //compiler error: assignment operator unavailable in C 
}

The MSVC9.0 (the C++ compiler of Visual Studio 2008) does generate the default constructor but is unable to generate copy and assignment operators for C although C is a friend of A. Is this the expected behavior or is this a Microsoft bug? I think the latter is the case, and if I am right, can anyone point to an article/forum/... where this issue is discussed or where microsoft has reacted to this bug. Thank you in advance.

P.S. Incidentally, if BOTH private inheritances are changed to protected, everything works

P.P.S. I need a proof, that the above code is legal OR illegal. It was indeed intended that a class with a virtual private base could not be derived from, as I understand. But they seem to have missed the friend part. So... here it goes, my first bounty :)


Solution

  • Your code compiles fine with Comeau Online, and also with MinGW g++ 4.4.1.

    I'm mentioning that just an "authority argument".

    From a standards POV access is orthogonal to virtual inheritance. The only problem with virtual inheritance is that it's the most derived class that initializes the virtually-derived-from class further up the inheritance chain (or "as if"). In your case the most derived class has the required access to do that, and so the code should compile.

    MSVC also has some other problems with virtual inheritance.

    So, yes,

    • the code is valid, and
    • it's an MSVC compiler bug.

    FYI, that bug is still present in MSVC 10.0. I found a bug report about a similar bug, confirmed by Microsoft. However, with just some cursory googling I couldn't find this particular bug.