The GCC 15 release series differs from previous GCC releases in a number of ways. Some of these are a result of bug fixing, and some old behaviors have been intentionally changed to support new standards, or relaxed in standards-conforming ways to facilitate compilation or run-time performance.
Some of these changes are user visible and can cause grief when porting to GCC 15. This document is an effort to identify common issues and provide solutions. Let us know if you have suggestions for improvements!
The meaning of function declarations of the form
rettype identifier ();
such as
char *strstr ();
changed in C23.
In C17 and earlier, such function declarators specified no information about the number or types of the parameters of the function (C17 6.7.6.3), requiring users to know the correct number of arguments, with each passed argument going through default argument promotion.
In C23 such declarations mean (void) i.e. a function taking
no arguments, which can lead to build failures on code that relied on
the earlier meaning, such as in
this example:
#include <signal.h>
void test()
{
void (*handler)();
handler = signal(SIGQUIT, SIG_IGN);
}
<source>: In function 'test':
<source>:6:11: error: assignment to 'void (*)(void)' from incompatible pointer type '__sighandler_t' {aka 'void (*)(int)'} [-Wincompatible-pointer-types]
6 | handler = signal(SIGQUIT, SIG_IGN);
| ^
In file included from <source>:1:
/usr/include/signal.h:72:16: note: '__sighandler_t' declared here
72 | typedef void (*__sighandler_t) (int);
| ^~~~~~~~~~~~~~
Code such as the above relying on a non-zero number of parameters (such
as a single int) can be fixed for C23 by adding the correct
parameters to the function declarator, such as via:
void (*handler)(int);
In other cases the code is simply missing a #include of
the correct header, such as with:
void *malloc();
These can be fixed by including the correct header and removing the non-prototype declaration.
Alternatively you can use -std= to select an earlier version of the C standard.
C23 added various new keywords, including
bool, true, false,
nullptr, and thread_local.
Code that uses these for identifiers will need changing.
For example typedef int bool; will
fail with:
<source>:1:13: error: 'bool' cannot be defined via 'typedef'
1 | typedef int bool;
| ^~~~
<source>:1:13: note: 'bool' is a keyword with '-std=c23' onwards
<source>:1:1: warning: useless type name in empty declaration
1 | typedef int bool;
| ^~~~~~~
In C99 and later you can use #include <stdbool.h>
which provides definitions of bool, true,
and false compatible with C23.
Note that the bool type is not the same
as int at ABI level, and so care may be needed porting
declarations that appear at an ABI boundary (or serialized to the
filesystem).
Note that all GCC releases make improvements to conformance which may reject non-conforming, legacy codebases.
Some C++ Standard Library headers have been changed to no longer include other headers that were being used internally by the library. As such, C++ programs that used standard library components without including the right headers will no longer compile.
In particular, the following headers are used less widely within libstdc++ and may need to be included explicitly when compiling with GCC 15:
<stdint.h>
(for int8_t, int32_t etc.)
and <cstdint>
(for std::int8_t, std::int32_t etc.)
<ostream>
(for std::endl, std::flush etc.)
Some C++ Standard Library headers now produce deprecation warnings when
included. The warnings suggest how to adjust the code to avoid the warning,
for example all uses of <cstdbool> and
<cstdalign> can simply be removed,
because they serve no purpose and are unnecessary in C++ programs.
Most uses of <ccomplex> can be adjusted to use
<complex> instead, and uses of <ctgmath>
can use <cmath> and/or <complex>.
std::vector
In GCC 15.1 (and GCC 14.3) std::vector has been extended so that
the vector(InputIterator, InputIterator) constructor recognizes
iterators that satisfy the C++20 iterator concepts, such as
std::random_access_iterator. This can give significant performance
improvements for some types of iterator which satisfy the new C++20 concepts
but which were only considered to be a Cpp17InputIterator under the
rules of C++17 (and earlier standards). However, it can also cause problems
for iterator adaptors or iterator facades implemented as templates that wrap
another iterator class.
If an adaptor template declares all the possible operators supported for any
iterator category (e.g. operator--, operator+,
operator[], etc.) but does not constrain those operators to only
be present when the wrapped iterator supports them, then the C++20 standard
library will incorrectly deduce that the adaptor satisfies the new C++20
iterator concepts. This means the library might attempt to use
operator-- on a non-bidirectional iterator,
or operator[] on a non-random access iterator, resulting in
compilation errors.
Code which encounters these errors should be fixed by constraining the iterator
adaptors using concepts (or std::enable_if) so that the operator
functions don't appear to be usable unless they will actually compile.
For example, the following additions could be used to prevent
IteratorAdaptor<Iter> from looking like it supports
operator--, operator[], and operator-
when Iter doesn't support those:
template<class Iter>
class IteratorAdaptor
{
Iter m_iter; // The underlying iterator that is being adapted.
public:
// ...
IteratorAdaptor& operator--()
(追記) #ifdef __cpp_lib_ranges
requires std::bidirectional_iterator<Iter>
#endif (追記ここまで)
{ --m_iter; return *this; }
reference operator[](difference_type n) const
(追記) #ifdef __cpp_lib_ranges
requires std::random_access_iterator<Iter>
#endif (追記ここまで)
{ return m_iter[n]; }
friend difference_type operator-(const IteratorAdaptor& lhs, const IteratorAdaptor& rhs)
(追記) #ifdef __cpp_lib_ranges
requires std::sized_sentinel_for<Iter, Iter>
#endif (追記ここまで)
{ return lhs.m_iter - rhs.m_iter; }
};
Copyright (C) Free Software Foundation, Inc. Verbatim copying and distribution of this entire article is permitted in any medium, provided this notice is preserved.
These pages are maintained by the GCC team. Last modified 2025年05月23日.