https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90960

            Bug ID: 90960
           Summary: declaring a member function with a computed typedef is
                    confused as a data member definition
           Product: gcc
           Version: 9.1.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: alisdairm at me dot com
  Target Milestone: ---

Note that this bug is a real corner case unlikely to occur in production code,
but bit us in experimental coding.  In fact, there are two bugs lurking in this
report (single test case), but it feels too obscure to tie up two issues!

The following program should compile equivalently, regardless of the definition
of the SHOW_BUG macro:

#include <type_traits>

#define SHOW_ERROR 1

using namespace std;

template <typename T>
struct why_me {

#if defined(SHOW_ERROR)
   using what_the = conditional_t<is_const_v<T>, void() noexcept, void()>;
#else
   using what_the = void() noexcept(is_const_v<T>);
#endif

   what_the heck;
};

template <typename T>
void why_me<T>::heck() noexcept(is_const_v<T>) {}

int main() {
   why_me<int> x = {};
   x.heck();

   why_me<int> y = {};
   y.heck();
}


However, when SHOW_ERROR is defined, we get the following errors:

to_heck_with_it.cpp:20:6: error: no declaration matches 'void
why_me<T>::heck()'
   20 | void why_me<T>::heck() noexcept(is_const_v<T>) {}
      |      ^~~~~~~~~
to_heck_with_it.cpp:16:13: note: candidate is: 'why_me<T>::what_the
why_me<T>::heck'
   16 |    what_the heck;
      |             ^~~~
to_heck_with_it.cpp:8:8: note: 'struct why_me<T>' defined here
    8 | struct why_me {
      |        ^~~~~~
to_heck_with_it.cpp: In instantiation of 'struct why_me<int>':
to_heck_with_it.cpp:23:16:   required from here
to_heck_with_it.cpp:16:13: error: field 'why_me<int>::heck' invalidly declared
function type
   16 |    what_the heck;
      |             ^~~~

It is not clear why the last error claims a function type is invalid here (I
believe it should be).


However, there is a second bug lurking when we do not define SHOW_ERROR (the
program compiles cleanly on other compilers):

to_heck_with_it.cpp:20:6: error: declaration of 'void why_me<T>::heck()
noexcept (is_const_v<T>)' has a different exception specifier
   20 | void why_me<T>::heck() noexcept(is_const_v<T>) {}
      |      ^~~~~~~~~
to_heck_with_it.cpp:16:13: note: from previous declaration 'void
why_me<T>::heck()'
   16 |    what_the heck;
      |             ^~~~

Here, the exception specifications are clearly the same, as they are even
spelled the same, so the error is just wrong.

Reply via email to