Bug 100381 - [11/12/13 Regression] new static_assert((std::__is_complete_or_unbounded(...)) failure from g++ 11.1.0
Summary: [11/12/13 Regression] new static_assert((std::__is_complete_or_unbounded(...)...
Status: UNCONFIRMED
Alias: None
Product: gcc
Classification: Unclassified
Component: libstdc++ (show other bugs)
Version: 11.1.0
: P3 normal
Target Milestone: 11.4
Assignee: Not yet assigned to anyone
URL:
Keywords: rejects-valid
Depends on:
Blocks:
 
Reported: 2021-05-02 14:15 UTC by Gilles Gouaillardet
Modified: 2022-04-28 14:59 UTC (History)
2 users (show)

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


Attachments
a reproducer that fails from g++ 11.1.0 (464 bytes, text/x-csrc)
2021-05-02 14:15 UTC, Gilles Gouaillardet
Details

Note You need to log in before you can comment on or make changes to this bug.
Description Gilles Gouaillardet 2021-05-02 14:15:15 UTC
Created attachment 50732 [details]
a reproducer that fails from g++ 11.1.0

g++ 11.1.0 is no more able to compile GROMACS, as reported at https://gitlab.com/gromacs/gromacs/-/issues/4039

I trimmed the offending code into the attached and self-contained reproducer, that fails to build with the following error:

$ g++ -c reproducer.cpp
In file included from /home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/move.h:57,
                 from /home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/stl_function.h:60,
                 from /home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/functional:49,
                 from reproducer.cpp:1:
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits: In instantiation of 'struct std::is_invocable_r<void, {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&, IndexGroupsAndNames>':
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:3011:46:   required from 'constexpr const bool std::is_invocable_r_v<void, {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&, IndexGroupsAndNames>'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/invoke.h:103:27:   required by substitution of 'template<class _Res, class _Callable, class ... _Args> constexpr std::enable_if_t<is_invocable_r_v<_Res, _Callable, _Args ...>, _Res> std::__invoke_r(_Callable&&, _Args&& ...) [with _Res = void; _Callable = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&; _Args = {IndexGroupsAndNames}]'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/std_function.h:291:30:   required from 'static _Res std::_Function_handler<_Res(_ArgTypes ...), _Functor>::_M_invoke(const std::_Any_data&, _ArgTypes&& ...) [with _Res = void; _Functor = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>; _ArgTypes = {IndexGroupsAndNames}]'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/std_function.h:422:21:   required from 'std::function<_Res(_ArgTypes ...)>::function(_Functor) [with _Functor = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>; <template-parameter-2-2> = void; <template-parameter-2-3> = void; _Res = void; _ArgTypes = {IndexGroupsAndNames}]'
reproducer.cpp:55:56:   required from here
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:2954:7: error: static assertion failed: each argument type must be a complete class or an unbounded array
 2954 |       static_assert((std::__is_complete_or_unbounded(
      |       ^~~~~~~~~~~~~
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:2954:7: note: 'std::__is_complete_or_unbounded<std::__type_identity<IndexGroupsAndNames> >((std::__type_identity<IndexGroupsAndNames>{}, std::__type_identity<IndexGroupsAndNames>()))' evaluates to false
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits: In instantiation of 'struct std::is_nothrow_invocable_r<void, {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&, IndexGroupsAndNames>':
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:3016:54:   required from 'constexpr const bool std::is_nothrow_invocable_r_v<void, {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&, IndexGroupsAndNames>'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/invoke.h:105:14:   required from 'constexpr std::enable_if_t<is_invocable_r_v<_Res, _Callable, _Args ...>, _Res> std::__invoke_r(_Callable&&, _Args&& ...) [with _Res = void; _Callable = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>&; _Args = {IndexGroupsAndNames}; std::enable_if_t<is_invocable_r_v<_Res, _Callable, _Args ...>, _Res> = void]'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/std_function.h:291:30:   required from 'static _Res std::_Function_handler<_Res(_ArgTypes ...), _Functor>::_M_invoke(const std::_Any_data&, _ArgTypes&& ...) [with _Res = void; _Functor = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>; _ArgTypes = {IndexGroupsAndNames}]'
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/bits/std_function.h:422:21:   required from 'std::function<_Res(_ArgTypes ...)>::function(_Functor) [with _Functor = {anonymous}::DensityFitting::subscribeToPreProcessingNotifications(MdModulesNotifier*)::<lambda(const IndexGroupsAndNames&)>; <template-parameter-2-2> = void; <template-parameter-2-3> = void; _Res = void; _ArgTypes = {IndexGroupsAndNames}]'
reproducer.cpp:55:56:   required from here
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:2992:7: error: static assertion failed: each argument type must be a complete class or an unbounded array
 2992 |       static_assert((std::__is_complete_or_unbounded(
      |       ^~~~~~~~~~~~~
/home/users/gilles/local/gcc-11.1.0/include/c++/11.1.0/type_traits:2992:7: note: 'std::__is_complete_or_unbounded<std::__type_identity<IndexGroupsAndNames> >((std::__type_identity<IndexGroupsAndNames>{}, std::__type_identity<IndexGroupsAndNames>()))' evaluates to false


The same code can be compiled with previous g++ versions (and many other compilers such as clang++).

A "fix" is to replace
class IndexGroupsAndNames;
with
class IndexGroupsAndNames {};


git bisect points to the following commit

commit c1fc9f6e10e646f01194c8f150affbc1cfbc404a
Author: Antony Polukhin <antoshkka@gmail.com>
Date:   Thu Sep 24 18:51:37 2020 +0100

    libstdc++: assert that type traits are not misused with incomplete types [PR 71579]


Based on the commit message and me being illiterate in modern C++, I cannot tell whether the reproducer is valid C++, or g++ is right about rejecting it.


Could you please assess the validity of the reproducer and rule g++ behavior w.r.t modern C++ standard?
Comment 1 Richard Biener 2021-07-28 07:06:46 UTC
GCC 11.2 is being released, retargeting bugs to GCC 11.3
Comment 2 Jonathan Wakely 2021-07-28 10:43:42 UTC
This is almost certainly invalid code. Implementations are not required to enforce the complete type precondition, so "other compilers don't reject it" doesn't mean much. If the code has undefined behaviour then it's conforming to accept it silently, or to reject it like this.

I haven't analyzed it in detail yet though.
Comment 3 Richard Biener 2022-04-21 07:49:26 UTC
GCC 11.3 is being released, retargeting bugs to GCC 11.4.