https://gcc.gnu.org/bugzilla/show_bug.cgi?id=121172
Bug ID: 121172
Summary: error: use of 'static constexpr method...' before
deduction of 'auto' WHEN upgrade to 15.1.0 :
different writing order have different impact
Product: gcc
Version: 15.1.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: c++
Assignee: unassigned at gcc dot gnu.org
Reporter: terryinzaghi at 163 dot com
Target Milestone: ---
x86-64 g++15.1.0 -std=c++23
https://godbolt.org/z/sK5EdernP
#include <cstdint>
#include <cstddef>
#include <type_traits>
#include <utility>
//--- This example can WORK in 14.2.0 14.3.0 , but failed in 15.1.0
template<typename... Ts> struct CanNotWork {
template<int64_t I> constexpr auto operator/(int) const {
return(CanNotWork<>{});
};
static constexpr auto static_method() {return 1;}; //--just return 1
template<typename... KeepItEmpty> using to_flike_t =
decltype(static_method());
};
/*
<source>:12:29: required from here
12 | return(CanNotWork<>{});
| ^
<source>:15:83: error: use of 'static constexpr auto
CanNotWork<Ts>::static_method() [with Ts = {}]' before deduction of 'auto'
15 | template<typename... KeepItEmpty> using to_flike_t =
decltype(static_method());
|
~~~~~~~~~~~~~^~
<source>:15:83: error: use of 'static constexpr auto
CanNotWork<Ts>::static_method() [with Ts = {}]' before deduction of 'auto'
<source>:15:83: error: use of 'static constexpr auto
CanNotWork<Ts>::static_method() [with Ts = {}]' before deduction of 'auto'
*/
WORKROUND0:
template<typename... Ts> struct CanWork0 {
template<int64_t I> constexpr auto operator/(int) const
{return(CanWork0<>{});};
static constexpr auto static_lmbd=[] {return 1;}; //--change static_method
to static_lambda will make it WORKED
template<typename... KeepItEmpty> using to_flike_t =
decltype(static_lmbd());
};
WORKROUND1:
template<typename... Ts> struct CanWork1 {
//template<int64_t I> constexpr auto operator/(int) const
{return(CanNotWork<>{});}; MOVE it AFTER static_method will make it WORKED
static constexpr auto static_method() {return 1;}; //--just return 1
template<int64_t I> constexpr auto operator/(int) const
{return(CanWork1<>{});}; //HERE can WORK
template<typename... KeepItEmpty> using to_flike_t =
decltype(static_method());
};
int main() {
}