Bug 79802

Summary: Conflicting declaration with function pointers/types
Product: gcc Reporter: Toni Neubert <lutztonineubert>
Component: c++Assignee: Not yet assigned to anyone <unassigned>
Status: RESOLVED FIXED    
Severity: normal CC: daniel.kruegler, webrown.cpp
Priority: P3 Keywords: rejects-valid
Version: 7.0.1   
Target Milestone: 8.0   
Host: Target:
Build: Known to work: 8.0
Known to fail: Last reconfirmed: 2018-02-27 00:00:00

Description Toni Neubert 2017-03-02 08:12:07 UTC
Using any g++ with flag -std=c++11 (14 or 17):

```
template<typename T>
struct Foo {
  void set(int i)  {
  }
  static constexpr decltype(&Foo<T>::set) i = &Foo<T>::set;
};

template<typename T>
constexpr decltype(&Foo<T>::set) Foo<T>::i;
```

Results in:

> conflicting declaration 'constexpr decltype (& Foo<T>::set(int))   Foo<T>::i'
> note: previous declaration as 'constexpr decltype (& Foo<T>::set(int)) Foo<T>::i'

The problem exists with c++1(1,4,7) since GCC 4.7. No problem with clang >= 3.2.

A annoying workaround is to use a typedef of the function (compiles fine):

```
template<typename T>
struct Foo {
  void set(int i)  {
  }

  typedef decltype(&Foo<T>::set) function_type;
  static constexpr function_type i = &Foo<T>::set;
};

template<typename T>
constexpr typename Foo<T>::function_type Foo<T>::i;
```

Maybe similar to:
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70943
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=57401

Please see also:
http://stackoverflow.com/questions/42534051/conflicting-declaration-for-static-variable-with-template-class
Comment 1 Jonathan Wakely 2018-02-27 13:33:37 UTC
Confirmed, but this seems to have been fixed on trunk by r251438
Comment 2 Andrew Pinski 2021-07-31 22:19:01 UTC
Fixed in GCC 8+.