On Mon, Aug 07, 2023 at 08:03:05PM -0700, Nikolas Klauser wrote: > Thanks for the answers! > > There are a few really interesting extensions that I would like to use: > > - inline variables > - variable templates > - `if constexpr` > - fold expressions > - conditional explicit > - static operator()
There are multiple problems. cat /tmp/test.h #pragma GCC system_header inline int a = 1; template <int N> int b = N; void foo () { if constexpr (true) {} } template <typename...A> bool bar (A... a) { return (... + a); } struct S { template <int N> explicit (N == 42) S (int (&)[N]) {} }; struct T { static constexpr bool operator () (S const &x, S const &y) { return false; }; }; void baz () { auto a = [](int x, int y) static { return x + y; }; } cat /tmp/test.C #include "/tmp/test.h" g++ -S -std=c++11 -o /tmp/test.{s,C} The above with GCC 13 doesn't give any warnings, but does with -Wsystem-headers: In file included from /tmp/test.C:1: /tmp/test.h:2:1: warning: inline variables are only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 2 | inline int a = 1; | ^~~~~~ /tmp/test.h:3:22: warning: variable templates only available with ‘-std=c++14’ or ‘-std=gnu++14’ [-Wc++14-extensions] 3 | template <int N> int b = N; | ^ /tmp/test.h: In function ‘void foo()’: /tmp/test.h:4:18: warning: ‘if constexpr’ only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 4 | void foo () { if constexpr (true) {} } | ^~~~~~~~~ /tmp/test.h: In function ‘bool bar(A ...)’: /tmp/test.h:5:59: warning: fold-expressions only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 5 | template <typename...A> bool bar (A... a) { return (... + a); } | ^ /tmp/test.h: At global scope: /tmp/test.h:6:29: warning: ‘explicit(bool)’ only available with ‘-std=c++20’ or ‘-std=gnu++20’ [-Wc++20-extensions] 6 | struct S { template <int N> explicit (N == 42) S (int (&)[N]) {} }; | ^~~~~~~~ /tmp/test.h:7:34: warning: ‘static constexpr bool T::operator()(const S&, const S&)’ may be a static member function only with ‘-std=c++23’ or ‘-std=gnu++23’ [-Wc++23-extensions] 7 | struct T { static constexpr bool operator () (S const &x, S const &y) { return false; }; }; | ^~~~~~~~ /tmp/test.h: In function ‘void baz()’: /tmp/test.h:8:41: warning: ‘static’ only valid in lambda with ‘-std=c++23’ or ‘-std=gnu++23’ [-Wc++23-extensions] 8 | void baz () { auto a = [](int x, int y) static { return x + y; }; } | ^~~~~~ and with -pedantic-errors -Wsystem-headers even errors: ./xg++ -B ./ -S /tmp/test.C -std=c++11 -pedantic-errors -Wsystem-headers In file included from /tmp/test.C:1: /tmp/test.h:2:1: error: inline variables are only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 2 | inline int a = 1; | ^~~~~~ /tmp/test.h:3:22: error: variable templates only available with ‘-std=c++14’ or ‘-std=gnu++14’ [-Wc++14-extensions] 3 | template <int N> int b = N; | ^ /tmp/test.h: In function ‘void foo()’: /tmp/test.h:4:18: error: ‘if constexpr’ only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 4 | void foo () { if constexpr (true) {} } | ^~~~~~~~~ /tmp/test.h: In function ‘bool bar(A ...)’: /tmp/test.h:5:59: error: fold-expressions only available with ‘-std=c++17’ or ‘-std=gnu++17’ [-Wc++17-extensions] 5 | template <typename...A> bool bar (A... a) { return (... + a); } | ^ /tmp/test.h: At global scope: /tmp/test.h:6:29: error: ‘explicit(bool)’ only available with ‘-std=c++20’ or ‘-std=gnu++20’ [-Wc++20-extensions] 6 | struct S { template <int N> explicit (N == 42) S (int (&)[N]) {} }; | ^~~~~~~~ /tmp/test.h:7:34: error: ‘static constexpr bool T::operator()(const S&, const S&)’ may be a static member function only with ‘-std=c++23’ or ‘-std=gnu++23’ [-Wc++23-extensions] 7 | struct T { static constexpr bool operator () (S const &x, S const &y) { return false; }; }; | ^~~~~~~~ /tmp/test.h: In function ‘void baz()’: /tmp/test.h:8:41: error: ‘static’ only valid in lambda with ‘-std=c++23’ or ‘-std=gnu++23’ [-Wc++23-extensions] 8 | void baz () { auto a = [](int x, int y) static { return x + y; }; } | ^~~~~~ (so one would need to figure out if __extension__ somewhere around would be able to quite that up or not, or #pragma GCC diagnostic ignored "-Wc++14-extensions" (and 17, 20 and 23). Also, static operator () is only in GCC 13 and later, earlier versions will error on that. The -Wc++*-extensions separate warnings are only in GCC 12 and later, before that it will be harder to quiet the warnings selectively. Similarly, conditional explicit is only GCC 9 and later, if constexpr and inline vars GCC 7 and later, fold expressions GCC 6 and later, and variable templates GCC 5 and later. And in C++98 some of these don't work at all, if constexpr and static lambdas (because constexpr isn't a keyword and lambdas aren't supported altogether). Jakub