Bug 113008 - Trivially default constructible requires default member initializer before the end of its enclosing class
Summary: Trivially default constructible requires default member initializer before th...
Status: UNCONFIRMED
Alias: None
Product: gcc
Classification: Unclassified
Component: c++ (show other bugs)
Version: 13.1.0
: P3 normal
Target Milestone: ---
Assignee: Not yet assigned to anyone
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2023-12-13 21:17 UTC by Barry Revzin
Modified: 2023-12-15 05:56 UTC (History)
2 users (show)

See Also:
Host:
Target:
Build:
Known to work:
Known to fail:
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Barry Revzin 2023-12-13 21:17:10 UTC
This is related to bugs PR96645 and PR88165.

Consider this:

#include <type_traits>

template <typename T, int N>
struct Array {
    T elems[N];
};

struct A {
    struct B {
        int i = 0;
    };

    static constexpr bool v1 = std::is_trivially_default_constructible_v<B>;
    static constexpr bool v2 = std::is_trivially_default_constructible_v<Array<B, 10>>;
};



Declaring v1 works (and it correctly evaluates to false).

Declaring v2 fails to compile entirely:

opt/compiler-explorer/gcc-trunk-20231213/include/c++/14.0.0/type_traits:3284:7:   required from 'constexpr const bool std::is_trivially_default_constructible_v<Array<A::B, 10> >'
 3284 |     = __is_trivially_constructible(_Tp);
      |       ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
<source>:14:37:   required from here
   14 |     static constexpr bool v2 = std::is_trivially_default_constructible_v<Array<B, 10>>;
      |                                     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/opt/compiler-explorer/gcc-trunk-20231213/include/c++/14.0.0/type_traits:3284:7: error: default member initializer for 'A::B::i' required before the end of its enclosing class
 3284 |     = __is_trivially_constructible(_Tp);
      |       ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
<source>:10:15: note: defined here
   10 |         int i = 0;
      |               ^~~~

If we know that B isn't trivially default constructible (A::v1 is initialized to false), then can't we likewise also know that Array<B, 10> isn't trivially default constructible?