Search code examples
c++c++11unionsin-class-initialization

C++11 "In class initialization" feature is not working for unions


Minimal code example:

struct B { 
  union U {
    struct S {} s;
    int i = 100;
  }
  u;  
};

Now if we declare a B obj; then the obj.u.i is assigned a garbage value instead of 100. See the demo here. (The garbage value differs based on optimization flags etc.).

Is the "In class initialization" feature supposed to work with unions.

  • If yes, then what is the correct syntax? Or is this a g++ bug?
  • If not then what int i = 100; does?

Solution

  • This looks like a GCC bug. The standard says (9.5p2):

    At most one non-static data member of a union may have a brace-or-equal-initializer.

    Otherwise, the rules are the same as for a regular class.

    EDIT: In addition, 12.6.2p8:

    In a non-delegating constructor, if a given non-static data member or base class is not designated by a mem-initializer-id (including the case where there is no mem-initializer-list because the constructor has no ctor-initializer) and the entity is not a virtual base class of an abstract class (10.4), then

    • if the entity is a non-static data member that has a brace-or-equal-initializer, the entity is initialized as specified in 8.5;
    • otherwise, if the entity is a variant member (9.5), no initialization is performed;
    • otherwise, the entity is default-initialized (8.5).

    Presumably the implicitly defined default constructor counts here. The i member meets the criteria in the first bullet point, so it's initialized like it were a regular class member. The s member matches the second bullet point, so it's left uninitialized.