| GCC(1) | GNU | GCC(1) |
Only the most useful options are listed here; see below for the remainder. g++ accepts mostly the same options as gcc.
Other options are passed on to one or more stages of processing. Some options control the preprocessor and others the compiler itself. Yet other options control the assembler and linker; most of these are not documented here, since you rarely need to use any of them.
Most of the command-line options that you can use with GCC are useful for C programs; when an option is only useful with another language (usually C++), the explanation says so explicitly. If the description for a particular option does not mention a source language, you can use that option with all supported languages.
The usual way to run GCC is to run the executable called gcc, or machine-gcc when cross-compiling, or machine-gcc-version to run a specific version of GCC. When you compile C++ programs, you should invoke GCC as g++ instead.
The gcc program accepts options and file names as operands. Many options have multi-letter names; therefore multiple single-letter options may not be grouped: -dv is very different from -d -v.
You can mix options and other arguments. For the most part, the order you use doesn't matter. Order does matter when you use several options of the same kind; for example, if you specify -L more than once, the directories are searched in the order specified. Also, the placement of the -l option is significant.
Many options have long names starting with -f or with -W---for example, -fmove-loop-invariants, -Wformat and so on. Most of these have both positive and negative forms; the negative form of -ffoo is -fno-foo. This manual documents only one of these two forms, whichever one is not the default.
Some options take one or more arguments typically separated either by a space or by the equals sign (=) from the option name. Unless documented otherwise, an argument can be either numeric or a string. Numeric arguments must typically be small unsigned decimal or hexadecimal integers. Hexadecimal arguments must begin with the 0x prefix. Arguments to options that specify a size threshold of some sort may be arbitrarily large decimal or hexadecimal integers followed by a byte size suffix designating a multiple of bytes such as "kB" and "KiB" for kilobyte and kibibyte, respectively, "MB" and "MiB" for megabyte and mebibyte, "GB" and "GiB" for gigabyte and gigibyte, and so on. Such arguments are designated by byte-size in the following text. Refer to the NIST, IEC, and other relevant national and international standards for the full listing and explanation of the binary and decimal byte size prefixes.

For any given input file, the file name suffix determines what kind of compilation is done:
You can specify the input language explicitly with the -x option:
c c-header cpp-output c++ c++-header c++-cpp-output objective-c objective-c-header objective-c-cpp-output objective-c++ objective-c++-header objective-c++-cpp-output assembler assembler-with-cpp ada d f77 f77-cpp-input f95 f95-cpp-input go brig
If you only want some of the stages of compilation, you can use -x (or filename suffixes) to tell gcc where to start, and one of the options -c, -S, or -E to say where gcc is to stop. Note that some combinations (for example, -x cpp-output -E) instruct gcc to do nothing at all.
By default, the object file name for a source file is made by replacing the suffix .c, .i, .s, etc., with .o.
Unrecognized input files, not requiring compilation or assembly, are ignored.
By default, the assembler file name for a source file is made by replacing the suffix .c, .i, etc., with .s.
Input files that don't require compilation are ignored.
Input files that don't require preprocessing are ignored.
If -o is not specified, the default is to put an executable file in a.out, the object file for source .suffix in source .o, its assembler file in source .s, a precompiled header file in source.suffix.gch, and all preprocessed C source on standard output.
These are the supported qualifiers:
Thus for example to display all the undocumented target-specific switches supported by the compiler, use:
--help=target,undocumented
The sense of a qualifier can be inverted by prefixing it with the ^ character, so for example to display all binary warning options (i.e., ones that are either on or off and that do not take an argument) that have a description, use:
--help=warnings,^joined,^undocumented
The argument to --help= should not consist solely of inverted qualifiers.
Combining several classes is possible, although this usually restricts the output so much that there is nothing to display. One case where it does work, however, is when one of the classes is target. For example, to display all the target-specific optimization options, use:
--help=target,optimizers
The --help= option can be repeated on the command line. Each successive use displays its requested class of options, skipping those that have already been displayed. If --help is also specified anywhere on the command line then this takes precedence over any --help= option.
If the -Q option appears on the command line before the --help= option, then the descriptive text displayed by --help= is changed. Instead of describing the displayed options, an indication is given as to whether the option is enabled, disabled or set to a specific value (assuming that the compiler knows this at the point where the --help= option is used).
Here is a truncated example from the ARM port of gcc:
% gcc -Q -mabi=2 --help=target -c The following options are target specific: -mabi= 2 -mabort-on-noreturn [disabled] -mapcs [disabled]
The output is sensitive to the effects of previous command-line options, so for example it is possible to find out which optimizations are enabled at -O2 by using:
-Q -O2 --help=optimizers
Alternatively you can discover which binary optimizations are enabled by -O3 by using:
gcc -c -Q -O3 --help=optimizers > /tmp/O3-opts gcc -c -Q -O2 --help=optimizers > /tmp/O2-opts diff /tmp/O2-opts /tmp/O3-opts | grep enabled
gcc -c t.c -wrapper gdb,--args
This invokes all subprograms of gcc under gdb --args, thus the invocation of cc1 is gdb --args cc1 ....
Options in file are separated by whitespace. A whitespace character may be included in an option by surrounding the entire option in either single or double quotes. Any character (including a backslash) may be included by prefixing the character to be included with a backslash. The file may itself contain additional @file options; any such options will be processed recursively.
However, the use of gcc does not add the C++ library. g++ is a program that calls GCC and automatically specifies linking against the C++ library. It treats .c, .h and .i files as C++ source files instead of C source files unless -x is used. This program is also useful when precompiling a C header file with a .h extension for use in C++ compilations. On many systems, g++ is also installed with the name c++.
When you compile C++ programs, you may specify many of the same command-line options that you use for compiling programs in any language; or command-line options meaningful for C and related languages; or options that are meaningful only for C++ programs.
This turns off certain features of GCC that are incompatible with ISO C90 (when compiling C code), or of standard C++ (when compiling C++ code), such as the "asm" and "typeof" keywords, and predefined macros such as "unix" and "vax" that identify the type of system you are using. It also enables the undesirable and rarely used ISO trigraph feature. For the C compiler, it disables recognition of C++ style // comments as well as the "inline" keyword.
The alternate keywords "__asm__", "__extension__", "__inline__" and "__typeof__" continue to work despite -ansi. You would not want to use them in an ISO C program, of course, but it is useful to put them in header files that might be included in compilations done with -ansi. Alternate predefined macros such as "__unix__" and "__vax__" are also available, with or without -ansi.
The -ansi option does not cause non-ISO programs to be rejected gratuitously. For that, -Wpedantic is required in addition to -ansi.
The macro "__STRICT_ANSI__" is predefined when the -ansi option is used. Some header files may notice this macro and refrain from declaring certain functions or defining certain macros that the ISO standard doesn't call for; this is to avoid interfering with any programs that might use these names for other things.
Functions that are normally built in but do not have semantics defined by ISO C (such as "alloca" and "ffs") are not built-in functions when -ansi is used.
The compiler can accept several base standards, such as c90 or c++98, and GNU dialects of those standards, such as gnu90 or gnu++98. When a base standard is specified, the compiler accepts all programs following that standard plus those using GNU extensions that do not contradict it. For example, -std=c90 turns off certain features of GCC that are incompatible with ISO C90, such as the "asm" and "typeof" keywords, but not other GNU extensions that do not have a meaning in ISO C90, such as omitting the middle term of a "?:" expression. On the other hand, when a GNU dialect of a standard is specified, all features supported by the compiler are enabled, even when those features change the meaning of the base standard. As a result, some strict-conforming programs may be rejected. The particular standard is used by -Wpedantic to identify which features are GNU extensions given that version of the standard. For example -std=gnu90 -Wpedantic warns about C++ style // comments, while -std=gnu99 -Wpedantic does not.
A value for this option must be provided; possible values are
Using this option is roughly equivalent to adding the "gnu_inline" function attribute to all inline functions.
The option -fno-gnu89-inline explicitly tells GCC to use the C99 semantics for "inline" when in C99 or gnu99 mode (i.e., it specifies the default behavior). This option is not supported in -std=c90 or -std=gnu90 mode.
The preprocessor macros "__GNUC_GNU_INLINE__" and "__GNUC_STDC_INLINE__" may be used to check which semantics are in effect for "inline" functions.
-fpermitted-flt-eval-methods specifies whether the compiler should allow only the values of "FLT_EVAL_METHOD" specified in C99/C11, or the extended set of values specified in ISO/IEC TS 18661-3.
style is either "c11" or "ts-18661-3" as appropriate.
The default when in a standards compliant mode (-std=c11 or similar) is -fpermitted-flt-eval-methods=c11. The default when in a GNU dialect (-std=gnu11 or similar) is -fpermitted-flt-eval-methods=ts-18661-3.
Besides declarations, the file indicates, in comments, the origin of each declaration (source file and line), whether the declaration was implicit, prototyped or unprototyped (I, N for new or O for old, respectively, in the first character after the line number and the colon), and whether it came from a declaration or a definition (C or F, respectively, in the following character). In the case of function definitions, a K&R-style list of arguments followed by their declarations is also provided, inside comments, after the declaration.
Although it is possible to define such a function, this is not very useful as it is not possible to read the arguments. This is only supported for C as this construct is allowed by C++.
In C++, this switch only affects the "typeof" keyword, since "asm" and "inline" are standard keywords. You may want to use the -fno-gnu-keywords flag instead, which has the same effect. In C99 mode (-std=c99 or -std=gnu99), this switch only affects the "asm" and "typeof" keywords, since "inline" is a standard keyword in ISO C99.
GCC normally generates special code to handle certain built-in functions more efficiently; for instance, calls to "alloca" may become single instructions which adjust the stack directly, and calls to "memcpy" may become inline copy loops. The resulting code is often both smaller and faster, but since the function calls no longer appear as such, you cannot set a breakpoint on those calls, nor can you change the behavior of the functions by linking with a different library. In addition, when a function is recognized as a built-in function, GCC may use information about that function to warn about problems with calls to that function, or to generate more efficient code, even if the resulting code still contains calls to that function. For example, warnings are given with -Wformat for bad calls to "printf" when "printf" is built in and "strlen" is known not to modify global memory.
With the -fno-builtin-function option only the built-in function function is disabled. function must not begin with __builtin_. If a function is named that is not built-in in this version of GCC, this option is ignored. There is no corresponding -fbuiltin-function option; if you wish to enable built-in functions selectively when using -fno-builtin or -ffreestanding, you may define macros such as:
#define abs(n) __builtin_abs ((n)) #define strcpy(d, s) __builtin_strcpy ((d), (s))
For more information on GCC's support for transactional memory,
Note that the transactional memory feature is not supported with non-call exceptions (-fnon-call-exceptions).
In C++ code, this allows member names in structures to be similar to previous types declarations.
typedef int UOW; struct ABC { UOW UOW; };
Some cases of unnamed fields in structures and unions are only accepted with this option.
Note that this option is off for all targets but x86 targets using ms-abi.
This enables -fms-extensions, permits passing pointers to structures with anonymous fields to functions that expect pointers to elements of the type of the field, and permits referring to anonymous fields declared using a typedef. This is only supported for C, not C++.
Each kind of machine has a default for what "char" should be. It is either like "unsigned char" by default or like "signed char" by default.
Ideally, a portable program should always use "signed char" or "unsigned char" when it depends on the signedness of an object. But many programs have been written to use plain "char" and expect it to be signed, or expect it to be unsigned, depending on the machines they were written for. This option, and its inverse, let you make such a program work with the opposite default.
The type "char" is always a distinct type from each of "signed char" or "unsigned char", even though its behavior is always just like one of those two.
Note that this is equivalent to -fno-unsigned-char, which is the negative form of -funsigned-char. Likewise, the option -fno-signed-char is equivalent to -funsigned-char.
Warning: the -fsso-struct switch causes GCC to generate code that is not binary compatible with code generated without it if the specified endianness is not the native endianness of the target.
g++ -g -fstrict-enums -O -c firstClass.C
In this example, only -fstrict-enums is an option meant only for C++ programs; you can use the other options with any language supported by GCC.
Some options for compiling C programs, such as -std, are also relevant for C++ programs.
Here is a list of options that are only for compiling C++ programs:
Version 0 refers to the version conforming most closely to the C++ ABI specification. Therefore, the ABI obtained using version 0 will change in different versions of G++ as ABI bugs are fixed.
Version 1 is the version of the C++ ABI that first appeared in G++ 3.2.
Version 2 is the version of the C++ ABI that first appeared in G++ 3.4, and was the default through G++ 4.9.
Version 3 corrects an error in mangling a constant address as a template argument.
Version 4, which first appeared in G++ 4.5, implements a standard mangling for vector types.
Version 5, which first appeared in G++ 4.6, corrects the mangling of attribute const/volatile on function pointer types, decltype of a plain decl, and use of a function parameter in the declaration of another parameter.
Version 6, which first appeared in G++ 4.7, corrects the promotion behavior of C++11 scoped enums and the mangling of template argument packs, const/static_cast, prefix ++ and --, and a class scope function used as a template argument.
Version 7, which first appeared in G++ 4.8, that treats nullptr_t as a builtin type and corrects the mangling of lambdas in default argument scope.
Version 8, which first appeared in G++ 4.9, corrects the substitution behavior of function types with function-cv-qualifiers.
Version 9, which first appeared in G++ 5.2, corrects the alignment of "nullptr_t".
Version 10, which first appeared in G++ 6.1, adds mangling of attributes that affect type identity, such as ia32 calling convention attributes (e.g. stdcall).
Version 11, which first appeared in G++ 7, corrects the mangling of sizeof... expressions and operator names. For multiple entities with the same name within a function, that are declared in different scopes, the mangling now changes starting with the twelfth occurrence. It also implies -fnew-inheriting-ctors.
Version 12, which first appeared in G++ 8, corrects the calling conventions for empty classes on the x86_64 target and for classes with only deleted copy/move constructors. It accidentally changes the calling convention for classes with a deleted copy constructor and a trivial move constructor.
Version 13, which first appeared in G++ 8.2, fixes the accidental change in version 12.
See also -Wabi.
With -fabi-version=0 (the default), this defaults to 11 (GCC 7 compatibility). If another ABI version is explicitly selected, this defaults to 0. For compatibility with GCC versions 3.2 through 4.9, use -fabi-compat-version=2.
If this option is not provided but -Wabi=n is, that version is used for compatibility aliases. If this option is provided along with -Wabi (without the version), the version from this option is used for the warning.
This flag is enabled by default for -std=c++17.
This option enables functions to be overloaded for ordinary and UTF-8 strings:
int f(const char *); // #1 int f(const char8_t *); // #2 int v1 = f("text"); // Calls #1 int v2 = f(u8"text"); // Calls #2
and introduces new signatures for user-defined literals:
int operator""_udl1(char8_t); int v3 = u8'x'_udl1; int operator""_udl2(const char8_t*, std::size_t); int v4 = u8"text"_udl2; template<typename T, T...> int operator""_udl3(); int v5 = u8"text"_udl3;
The change to the types of UTF-8 string and character literals introduces incompatibilities with ISO C++11 and later standards. For example, the following code is well-formed under ISO C++11, but is ill-formed when -fchar8_t is specified.
char ca[] = u8"xx"; // error: char-array initialized from wide // string const char *cp = u8"xx";// error: invalid conversion from // `const char8_t*' to `const char*' int f(const char*); auto v = f(u8"xx"); // error: invalid conversion from // `const char8_t*' to `const char*' std::string s{u8"xx"}; // error: no matching function for call to // `std::basic_string<char>::basic_string()' using namespace std::literals; s = u8"xx"s; // error: conversion from // `basic_string<char8_t>' to non-scalar // type `basic_string<char>' requested
template <class T> concept bool Addable = requires (T t) { t + t; }; template <Addable T> T add (T a, T b) { return a + b; }
template <class T> auto forward(T t) -> decltype (realfn (t)) { return realfn (t); } void f() { forward({1,2}); // call forward<std::initializer_list<int>> }
This deduction was implemented as a possible extension to the originally proposed semantics for the C++11 standard, but was not part of the final standard, so it is disabled by default. This option is deprecated, and may be removed in a future version of G++.
In C++17, the compiler is required to omit these temporaries, but this option still affects trivial member functions.
On targets that support symbol aliases, the default is -fextern-tls-init. On targets that do not support symbol aliases, the default is -fno-extern-tls-init.
Mixing code compiled with -frtti with that compiled with -fno-rtti may not work. For example, programs may fail to link if a class compiled with -fno-rtti is used as a base for a class compiled with -frtti.
void operator delete (void *, std::size_t) noexcept; void operator delete[] (void *, std::size_t) noexcept;
as introduced in C++14. This is useful for user-defined replacement deallocation functions that, for example, use the size of the object to make deallocation faster. Enabled by default under -std=c++14 and above. The flag -Wsized-deallocation warns about places that might want to add a definition.
The effect of this is that GCC may, effectively, mark inline methods with "__attribute__ ((visibility ("hidden")))" so that they do not appear in the export table of a DSO and do not require a PLT indirection when used within the DSO. Enabling this option can have a dramatic effect on load and link times of a DSO as it massively reduces the size of the dynamic export table when the library makes heavy use of templates.
The behavior of this switch is not quite the same as marking the methods as hidden directly, because it does not affect static variables local to the function or cause the compiler to deduce that the function is defined in only one shared object.
You may mark a method as having a visibility explicitly to negate the effect of the switch for that method. For example, if you do want to compare pointers to a particular inline method, you might mark it as having default visibility. Marking the enclosing class with explicit visibility has no effect.
Explicitly instantiated inline methods are unaffected by this option as their linkage might otherwise cross a shared library boundary.
The flag makes these changes to GCC's linkage model:
In new code it is better to use -fvisibility=hidden and export those classes that are intended to be externally visible. Unfortunately it is possible for code to rely, perhaps accidentally, on the Visual Studio behavior.
Among the consequences of these changes are that static data members of the same type with the same name but defined in different shared objects are different, so changing one does not change the other; and that pointers to function members defined in different shared objects may not compare equal. When this flag is given, it is a violation of the ODR to define types with the same name differently.
In addition, these optimization, warning, and code generation options have meanings only for C++ programs:
-Wabi can also be used with an explicit version number to warn about compatibility with a particular -fabi-version level, e.g. -Wabi=2 to warn about changes relative to -fabi-version=2.
If an explicit version number is provided and -fabi-compat-version is not specified, the version number from this option is used for compatibility aliases. If no explicit version number is provided with this option, but -fabi-compat-version is specified, that version number is used for ABI warnings.
Although an effort has been made to warn about all such cases, there are probably some cases that are not warned about, even though G++ is generating incompatible code. There may also be cases where warnings are emitted even though the code that is generated is compatible.
You should rewrite your code to avoid these warnings if you are concerned about the fact that code generated by G++ may not be binary compatible with code generated by other compilers.
Known incompatibilities in -fabi-version=2 (which was the default from GCC 3.4 to 4.9) include:
extern int N; template <int &> struct S {}; void n (S<N>) {2}
This was fixed in -fabi-version=3.
The mangling was changed in -fabi-version=4.
These mangling issues were fixed in -fabi-version=5.
Also, the ABI changed the mangling of template argument packs, "const_cast", "static_cast", prefix increment/decrement, and a class scope function used as a template argument.
These issues were corrected in -fabi-version=6.
These issues were corrected in -fabi-version=7.
This was fixed in -fabi-version=8, the default for GCC 5.1.
This was fixed in -fabi-version=9, the default for GCC 5.2.
This was fixed in -fabi-version=10, the default for GCC 6.1.
It also warns about psABI-related changes. The known psABI changes at this point include:
union U { long double ld; int i; };
"union U" is always passed in memory.
// li's initial underlying array lives as long as li std::initializer_list<int> li = { 1,2,3 }; // assignment changes li to point to a temporary array li = { 4, 5 }; // now the temporary is gone and li has a dangling pointer int i = li.begin()[0] // undefined behavior
#define __STDC_FORMAT_MACROS #include <inttypes.h> #include <stdio.h> int main() { int64_t i64 = 123; printf("My int64: %" PRId64"\n", i64); }
In this case, "PRId64" is treated as a separate preprocessing token.
Additionally, warn when a user-defined literal operator is declared with a literal suffix identifier that doesn't begin with an underscore. Literal suffix identifiers that don't begin with an underscore are reserved for future standardization.
This warning is enabled by default.
With -Wnarrowing in C++98, warn when a narrowing conversion prohibited by C++11 occurs within { }, e.g.
int i = { 2.2 }; // error: narrowing from double to int
This flag is included in -Wall and -Wc++11-compat.
As an example:
template <class T> void f(T t) { t(); }; void g() noexcept; void h() { f(g); }
In C++14, "f" calls "f<void(*)()>", but in C++17 it calls "f<void(*)()noexcept>".
std::string str = "abc"; memset (&str, 0, sizeof str);
The -Wclass-memaccess option is enabled by -Wall. Explicitly casting the pointer to the class object to "void *" or to a type that can be safely accessed by the raw memory function suppresses the warning.
struct A { int i; int j; A(): j (0), i (1) { } };
The compiler rearranges the member initializers for "i" and "j" to match the declaration order of the members, emitting a warning to that effect. This warning is enabled by -Wall.
struct T { ... }; T fn() { T t; ... return std::move (t); }
But in this example, the "std::move" call prevents copy elision.
This warning is enabled by -Wall.
struct T { ... }; T fn(T t) { ... return std::move (t); }
Here, the "std::move" call is redundant. Because G++ implements Core Issue 1579, another example is:
struct T { // convertible to U ... }; struct U { ... }; U fn() { T t; ... return std::move (t); }
In this example, copy elision isn't applicable because the type of the expression being returned and the function return type differ, yet G++ treats the return value as if it were designated by an rvalue.
This warning is enabled by -Wextra.
The following -W... options are not affected by -Wall.
This option also enables -Wnon-virtual-dtor, which is also one of the effective C++ recommendations. However, the check is extended to warn about the lack of virtual destructor in accessible non-polymorphic bases classes too.
When selecting this option, be aware that the standard library headers do not obey all of these guidelines; use grep -v to filter out those warnings.
struct A { virtual void f(); }; struct B: public A { void f(int); };
the "A" class version of "f" is hidden in "B", and code like:
B* b; b->f();
fails to compile.
This section describes the command-line options that are only meaningful for Objective-C and Objective-C++ programs. You can also use most of the language-independent GNU compiler options. For example, you might compile a file some_class.m like this:
gcc -g -fgnu-runtime -O -c some_class.m
In this example, -fgnu-runtime is an option meant only for Objective-C and Objective-C++ programs; you can use the other options with any language supported by GCC.
Note that since Objective-C is an extension of the C language, Objective-C compilations may also use options specific to the C front-end (e.g., -Wtraditional). Similarly, Objective-C++ compilations may use C++-specific options (e.g., -Wabi).
Here is a list of options that are only for compiling Objective-C and Objective-C++ programs:
The "- (id) .cxx_construct" and "- (void) .cxx_destruct" methods thusly generated only operate on instance variables declared in the current Objective-C class, and not those inherited from superclasses. It is the responsibility of the Objective-C runtime to invoke all such methods in an object's inheritance hierarchy. The "- (id) .cxx_construct" methods are invoked by the runtime immediately after a new object instance is allocated; the "- (void) .cxx_destruct" methods are invoked immediately before the runtime deallocates an object instance.
As of this writing, only the NeXT runtime on Mac OS X 10.4 and later has support for invoking the "- (id) .cxx_construct" and "- (void) .cxx_destruct" methods.
Note - this option also affects the display of the #error and #warning pre-processor directives, and the deprecated function/type/variable attribute. It does not however affect the pragma GCC warning and pragma GCC error pragmas.
The colors are defined by the environment variable GCC_COLORS. Its value is a colon-separated list of capabilities and Select Graphic Rendition (SGR) substrings. SGR commands are interpreted by the terminal or terminal emulator. (See the section in the documentation of your text terminal for permitted values and their meanings as character attributes.) These substring values are integers in decimal representation and can be concatenated with semicolons. Common values to concatenate include 1 for bold, 4 for underline, 5 for blink, 7 for inverse, 39 for default foreground color, 30 to 37 for foreground colors, 90 to 97 for 16-color mode foreground colors, 38;5;0 to 38;5;255 for 88-color and 256-color modes foreground colors, 49 for default background color, 40 to 47 for background colors, 100 to 107 for 16-color mode background colors, and 48;5;0 to 48;5;255 for 88-color and 256-color modes background colors.
The default GCC_COLORS is
error=01;31:warning=01;35:note=01;36:range1=32:range2=34:locus=01:\ quote=01:fixit-insert=32:fixit-delete=31:\ diff-filename=01:diff-hunk=32:diff-delete=31:diff-insert=32:\ type-diff=01;32
where 01;31 is bold red, 01;35 is bold magenta, 01;36 is bold cyan, 32 is green, 34 is blue, 01 is bold, and 31 is red. Setting GCC_COLORS to the empty string disables colors. Supported capabilities are as follows.
printf ("foo %s bar", long_i + long_j); ~^ ~~~~~~~~~~~~~~~ | | char * long int
This option suppresses the printing of these labels (in the example above, the vertical bars and the "char *" and "long int" text).
fix-it:"test.c":{45:3-45:21}:"gtk_widget_show_all"
The location is expressed as a half-open range, expressed as a count of bytes, starting at byte 1 for the initial column. In the above example, bytes 3 through 20 of line 45 of "test.c" are to be replaced with the given string:
00000000011111111112222222222<PHONE_NUMBER>1234567890123456789 gtk_widget_showall (dlg); ^^^^^^^^^^^^^^^^^^ gtk_widget_show_all
The filename and replacement string escape backslash as "\\", tab as "\t", newline as "\n", double quotes as "\"", non-printable characters as octal (e.g. vertical tab as "\013").
An empty replacement string indicates that the given range is to be removed. An empty range (e.g. "45:3-45:3") indicates that the string is to be inserted at the given position.
--- test.c +++ test.c @ -42,5 +42,5 @ void show_cb(GtkDialog *dlg) { - gtk_widget_showall(dlg); + gtk_widget_show_all(dlg); }
The diff may or may not be colorized, following the same rules as for diagnostics (see -fdiagnostics-color).
could not convert 'std::map<int, std::vector<double> >()' from 'map<[...],vector<double>>' to 'map<[...],vector<float>>
the -fdiagnostics-show-template-tree flag enables printing a tree-like structure showing the common and differing parts of the types, such as:
map< [...], vector< [double != float]>>
The parts that differ are highlighted with color ("double" and "float" in this case).
could not convert 'std::map<int, std::vector<double> >()' from 'map<[...],vector<double>>' to 'map<[...],vector<float>>
Specifying the -fno-elide-type flag suppresses that behavior. This flag also affects the output of the -fdiagnostics-show-template-tree flag.
The json format consists of a top-level JSON array containing JSON objects representing the diagnostics.
The JSON is emitted as one line, without formatting; the examples below have been formatted for clarity.
Diagnostics can have child diagnostics. For example, this error and note:
misleading-indentation.c:15:3: warning: this 'if' clause does not guard... [-Wmisleading-indentation] 15 | if (flag) | ^~ misleading-indentation.c:17:5: note: ...this statement, but the latter is misleadingly indented as if it were guarded by the 'if' 17 | y = 2; | ^
might be printed in JSON form (after formatting) like this:
[ { "kind": "warning", "locations": [ { "caret": { "column": 3, "file": "misleading-indentation.c", "line": 15 }, "finish": { "column": 4, "file": "misleading-indentation.c", "line": 15 } } ], "message": "this \u2018if\u2019 clause does not guard...", "option": "-Wmisleading-indentation", "children": [ { "kind": "note", "locations": [ { "caret": { "column": 5, "file": "misleading-indentation.c", "line": 17 } } ], "message": "...this statement, but the latter is ..." } ] }, ... ]
where the "note" is a child of the "warning".
A diagnostic has a "kind". If this is "warning", then there is an "option" key describing the command-line option controlling the warning.
A diagnostic can contain zero or more locations. Each location has up to three positions within it: a "caret" position and optional "start" and "finish" positions. A location can also have an optional "label" string. For example, this error:
bad-binary-ops.c:64:23: error: invalid operands to binary + (have 'S' {aka 'struct s'} and 'T' {aka 'struct t'}) 64 | return callee_4a () + callee_4b (); | ~~~~~~~~~~~~ ^ ~~~~~~~~~~~~ | | | | | T {aka struct t} | S {aka struct s}
has three locations. Its primary location is at the "+" token at column 23. It has two secondary locations, describing the left and right-hand sides of the expression, which have labels. It might be printed in JSON form as:
{ "children": [], "kind": "error", "locations": [ { "caret": { "column": 23, "file": "bad-binary-ops.c", "line": 64 } }, { "caret": { "column": 10, "file": "bad-binary-ops.c", "line": 64 }, "finish": { "column": 21, "file": "bad-binary-ops.c", "line": 64 }, "label": "S {aka struct s}" }, { "caret": { "column": 25, "file": "bad-binary-ops.c", "line": 64 }, "finish": { "column": 36, "file": "bad-binary-ops.c", "line": 64 }, "label": "T {aka struct t}" } ], "message": "invalid operands to binary + ..." }
If a diagnostic contains fix-it hints, it has a "fixits" array, consisting of half-open intervals, similar to the output of -fdiagnostics-parseable-fixits. For example, this diagnostic with a replacement fix-it hint:
demo.c:8:15: error: 'struct s' has no member named 'colour'; did you mean 'color'? 8 | return ptr->colour; | ^~~~~~ | color
might be printed in JSON form as:
{ "children": [], "fixits": [ { "next": { "column": 21, "file": "demo.c", "line": 8 }, "start": { "column": 15, "file": "demo.c", "line": 8 }, "string": "color" } ], "kind": "error", "locations": [ { "caret": { "column": 15, "file": "demo.c", "line": 8 }, "finish": { "column": 20, "file": "demo.c", "line": 8 } } ], "message": "\u2018struct s\u2019 has no member named ..." }
where the fix-it hint suggests replacing the text from "start" up to but not including "next" with "string"'s value. Deletions are expressed via an empty value for "string", insertions by having "start" equal "next".
The following language-independent options do not enable specific warnings but control the kinds of diagnostics produced by GCC.
The warning message for each controllable warning includes the option that controls the warning. That option can then be used with -Werror= and -Wno-error= as described above. (Printing of the option in the warning message can be disabled using the -fno-diagnostics-show-option flag.)
Note that specifying -Werror=foo automatically implies -Wfoo. However, -Wno-error=foo does not imply anything.
You can request many specific warnings with options beginning with -W, for example -Wimplicit to request warnings on implicit declarations. Each of these specific warning options also has a negative form beginning -Wno- to turn off warnings; for example, -Wno-implicit. This manual lists only one of the two forms, whichever is not the default. For further language-specific options also refer to C++ Dialect Options and Objective-C and Objective-C++ Dialect Options.
Some options, such as -Wall and -Wextra, turn on other options, such as -Wunused, which may turn on further options, such as -Wunused-value. The combined effect of positive and negative forms is that more specific options have priority over less specific ones, independently of their position in the command-line. For options of the same specificity, the last one takes effect. Options enabled or disabled via pragmas take effect as if they appeared at the end of the command-line.
When an unrecognized warning option is requested (e.g., -Wunknown-warning), GCC emits a diagnostic stating that the option is not recognized. However, if the -Wno- form is used, the behavior is slightly different: no diagnostic is produced for -Wno-unknown-warning unless other diagnostics are being produced. This allows the use of new -Wno- options with old compilers, but if something goes wrong, the compiler warns that an unrecognized option is present.
Valid ISO C and ISO C++ programs should compile properly with or without this option (though a rare few require -ansi or a -std option specifying the required version of ISO C). However, without this option, certain GNU extensions and traditional C and C++ features are supported as well. With this option, they are rejected.
-Wpedantic does not cause warning messages for use of the alternate keywords whose names begin and end with __. Pedantic warnings are also disabled in the expression that follows "__extension__". However, only system header files should use these escape routes; application programs should avoid them.
Some users try to use -Wpedantic to check programs for strict ISO C conformance. They soon find that it does not do quite what they want: it finds some non-ISO practices, but not all---only those for which ISO C requires a diagnostic, and some others for which diagnostics have been added.
A feature to report any failure to conform to ISO C might be useful in some instances, but would require considerable additional work and would be quite different from -Wpedantic. We don't have plans to support such a feature in the near future.
Where the standard specified with -std represents a GNU extended dialect of C, such as gnu90 or gnu99, there is a corresponding base standard, the version of ISO C on which the GNU extended dialect is based. Warnings from -Wpedantic are given where they are required by the base standard. (It does not make sense for such warnings to be given only for features not in the specified GNU C dialect, since by definition the GNU dialects of C include all features the compiler supports with the given option, and there would be nothing to warn about.)
-Wall turns on the following warning flags:
-Waddress -Warray-bounds=1 (only with -O2) -Wbool-compare -Wbool-operation -Wc++11-compat -Wc++14-compat -Wcatch-value (C++ and Objective-C++ only) -Wchar-subscripts -Wcomment -Wduplicate-decl-specifier (C and Objective-C only) -Wenum-compare (in C/ObjC; this is on by default in C++) -Wformat -Wint-in-bool-context -Wimplicit (C and Objective-C only) -Wimplicit-int (C and Objective-C only) -Wimplicit-function-declaration (C and Objective-C only) -Winit-self (only for C++) -Wlogical-not-parentheses -Wmain (only for C/ObjC and unless -ffreestanding) -Wmaybe-uninitialized -Wmemset-elt-size -Wmemset-transposed-args -Wmisleading-indentation (only for C/C++) -Wmissing-attributes -Wmissing-braces (only for C/ObjC) -Wmultistatement-macros -Wnarrowing (only for C++) -Wnonnull -Wnonnull-compare -Wopenmp-simd -Wparentheses -Wpessimizing-move (only for C++) -Wpointer-sign -Wreorder -Wrestrict -Wreturn-type -Wsequence-point -Wsign-compare (only in C++) -Wsizeof-pointer-div -Wsizeof-pointer-memaccess -Wstrict-aliasing -Wstrict-overflow=1 -Wswitch -Wtautological-compare -Wtrigraphs -Wuninitialized -Wunknown-pragmas -Wunused-function -Wunused-label -Wunused-value -Wunused-variable -Wvolatile-register-var
Note that some warning flags are not implied by -Wall. Some of them warn about constructions that users generally do not consider questionable, but which occasionally you might wish to check for; others warn about constructions that are necessary or hard to avoid in some cases, and there is no simple way to modify the code to suppress the warning. Some of them are enabled by -Wextra but many of them must be enabled individually.
-Wclobbered -Wcast-function-type -Wdeprecated-copy (C++ only) -Wempty-body -Wignored-qualifiers -Wimplicit-fallthrough=3 -Wmissing-field-initializers -Wmissing-parameter-type (C only) -Wold-style-declaration (C only) -Woverride-init -Wsign-compare (C only) -Wredundant-move (only for C++) -Wtype-limits -Wuninitialized -Wshift-negative-value (in C++03 and in C99 and newer) -Wunused-parameter (only with -Wunused or -Wall) -Wunused-but-set-parameter (only with -Wunused or -Wall)
The option -Wextra also prints warning messages for the following cases:
Suppress warning messages emitted by "#warning" directives.
It is easy to accidentally do computations with "double" because floating-point literals are implicitly of type "double". For example, in:
float area(float radius) { return 3.14159 * radius * radius; }
the compiler performs the entire computation with "double" because the floating-point literal is a "double".
The formats are checked against the format features supported by GNU libc version 2.2. These include all ISO C90 and C99 features, as well as features from the Single Unix Specification and some BSD and GNU extensions. Other library implementations may not support all these features; GCC does not support warning about features that go beyond a particular library's limitations. However, if -Wpedantic is used with -Wformat, warnings are given about format features not in the selected standard version (but not for "strfmon" formats, since those are not in any version of the C standard).
Where the unused arguments lie between used arguments that are specified with $ operand number specifications, normally warnings are still given, since the implementation could not know what type to pass to "va_arg" to skip the unused arguments. However, in the case of "scanf" formats, this option suppresses the warning if the unused arguments are all pointers, since the Single Unix Specification says that such unused arguments are allowed.
void f (int a, int b) { char buf [13]; sprintf (buf, "a = %i, b = %i\n", a, b); }
At level 2, the call in the example above is again diagnosed, but this time because with a equal to a 32-bit "INT_MIN" the first %i directive will write some of its digits beyond the end of the destination buffer. To make the call safe regardless of the values of the two variables, the size of the destination buffer must be increased to at least 34 bytes. GCC includes the minimum size of the buffer in an informational note following the warning.
An alternative to increasing the size of the destination buffer is to constrain the range of formatted values. The maximum length of string arguments can be bounded by specifying the precision in the format directive. When numeric arguments of format directives can be assumed to be bounded by less than the precision of their type, choosing an appropriate length modifier to the format specifier will reduce the required buffer size. For example, if a and b in the example above can be assumed to be within the precision of the "short int" type then using either the %hi format directive or casting the argument to "short" reduces the maximum required size of the buffer to 24 bytes.
void f (int a, int b) { char buf [23]; sprintf (buf, "a = %hi, b = %i\n", a, (short)b); }
-Wnonnull is included in -Wall and -Wformat. It can be disabled with the -Wno-nonnull option.
-Wnonnull-compare is included in -Wall. It can be disabled with the -Wno-nonnull-compare option.
For example, GCC warns about "i" being uninitialized in the following snippet only when -Winit-self has been specified:
int f() { int i = i; return i; }
This warning is enabled by -Wall in C++.
switch (cond) { case 1: a = 1; break; case 2: a = 2; case 3: a = 3; break; }
This warning does not warn when the last statement of a case cannot fall through, e.g. when there is a return statement or a call to function declared with the noreturn attribute. -Wimplicit-fallthrough= also takes into account control flow statements, such as ifs, and only warns when appropriate. E.g.
switch (cond) { case 1: if (i > 3) { bar (5); break; } else if (i < 1) { bar (0); } else return; default: ... }
Since there are occasions where a switch case fall through is desirable, GCC provides an attribute, "__attribute__ ((fallthrough))", that is to be used along with a null statement to suppress this warning that would normally occur:
switch (cond) { case 1: bar (0); __attribute__ ((fallthrough)); default: ... }
C++17 provides a standard way to suppress the -Wimplicit-fallthrough warning using "[[fallthrough]];" instead of the GNU attribute. In C++11 or C++14 users can use "[[gnu::fallthrough]];", which is a GNU extension. Instead of these attributes, it is also possible to add a fallthrough comment to silence the warning. The whole body of the C or C++ style comment should match the given regular expressions listed below. The option argument n specifies what kind of comments are accepted:
The comment needs to be followed after optional whitespace and other comments by "case" or "default" keywords or by a user label that precedes some "case" or "default" label.
switch (cond) { case 1: bar (0); /* FALLTHRU */ default: ... }
The -Wimplicit-fallthrough=3 warning is enabled by -Wextra.
This warning is also enabled by -Wextra.
In the following example, the call to "bar" is misleadingly indented as if it were guarded by the "if" conditional.
if (some_condition ()) foo (); bar (); /* Gotcha: this is not guarded by the "if". */
In the case of mixed tabs and spaces, the warning uses the -ftabstop= option to determine if the statements line up (defaulting to 8).
The warning is not issued for code involving multiline preprocessor logic such as the following example.
if (flagA) foo (0); #if SOME_CONDITION_THAT_DOES_NOT_HOLD if (flagB) #endif foo (1);
The warning is not issued after a "#line" directive, since this typically indicates autogenerated code, and no assumptions can be made about the layout of the file that the directive references.
This warning is enabled by -Wall in C and C++.
In C++, the warning is issued when an explicit specialization of a primary template declared with attribute "alloc_align", "alloc_size", "assume_aligned", "format", "format_arg", "malloc", or "nonnull" is declared without it. Attributes "deprecated", "error", and "warning" suppress the warning..
You can use the "copy" attribute to apply the same set of attributes to a declaration as that on another declaration without explicitly enumerating the attributes. This attribute can be applied to declarations of functions, variables, or types.
-Wmissing-attributes is enabled by -Wall.
For example, since the declaration of the primary function template below makes use of both attribute "malloc" and "alloc_size" the declaration of the explicit specialization of the template is diagnosed because it is missing one of the attributes.
template <class T> T* __attribute__ ((malloc, alloc_size (1))) allocate (size_t); template <> void* __attribute__ ((malloc)) // missing alloc_size allocate<void> (size_t);
int a[2][2] = { 0, 1, 2, 3 }; int b[2][2] = { { 0, 1 }, { 2, 3 } };
This warning is enabled by -Wall.
For example:
#define DOIT x++; y++ if (c) DOIT;
will increment "y" unconditionally, not just when "c" holds. The can usually be fixed by wrapping the macro in a do-while loop:
#define DOIT do { x++; y++; } while (0) if (c) DOIT;
This warning is enabled by -Wall in C and C++.
Also warn if a comparison like "x<=y<=z" appears; this is equivalent to "(x<=y ? 1 : 0) <= z", which is a different interpretation from that of ordinary mathematical notation.
Also warn for dangerous uses of the GNU extension to "?:" with omitted middle operand. When the condition in the "?": operator is a boolean expression, the omitted value is always 1. Often programmers expect it to be a value computed inside the conditional expression instead.
For C++ this also warns for some cases of unnecessary parentheses in declarations, which can indicate an attempt at a function call instead of a declaration:
{ // Declares a local variable called mymutex. std::unique_lock<std::mutex> (mymutex); // User meant std::unique_lock<std::mutex> lock (mymutex); }
This warning is enabled by -Wall.
The C and C++ standards define the order in which expressions in a C/C++ program are evaluated in terms of sequence points, which represent a partial ordering between the execution of parts of the program: those executed before the sequence point, and those executed after it. These occur after the evaluation of a full expression (one which is not part of a larger expression), after the evaluation of the first operand of a "&&", "||", "? :" or "," (comma) operator, before a function is called (but after the evaluation of its arguments and the expression denoting the called function), and in certain other places. Other than as expressed by the sequence point rules, the order of evaluation of subexpressions of an expression is not specified. All these rules describe only a partial order rather than a total order, since, for example, if two functions are called within one expression with no sequence point between them, the order in which the functions are called is not specified. However, the standards committee have ruled that function calls do not overlap.
It is not specified when between sequence points modifications to the values of objects take effect. Programs whose behavior depends on this have undefined behavior; the C and C++ standards specify that "Between the previous and next sequence point an object shall have its stored value modified at most once by the evaluation of an expression. Furthermore, the prior value shall be read only to determine the value to be stored.". If a program breaks these rules, the results on any particular implementation are entirely unpredictable.
Examples of code with undefined behavior are "a = a++;", "a[n] = b[n++]" and "a[i++] = i;". Some more complicated cases are not diagnosed by this option, and it may give an occasional false positive result, but in general it has been found fairly effective at detecting this sort of problem in programs.
The C++17 standard will define the order of evaluation of operands in more cases: in particular it requires that the right-hand side of an assignment be evaluated before the left-hand side, so the above examples are no longer undefined. But this warning will still warn about them, to help people avoid writing code that is undefined in C and earlier revisions of C++.
The standard is worded confusingly, therefore there is some debate over the precise meaning of the sequence point rules in subtle cases. Links to discussions of the problem, including proposed formal definitions, may be found on the GCC readings page, at <http://gcc.gnu.org/readings.html>.
This warning is enabled by -Wall for C and C++.
For C only, warn about a "return" statement with an expression in a function whose return type is "void", unless the expression type is also "void". As a GNU extension, the latter case is accepted without a warning unless -Wpedantic is used. Attempting to use the return value of a non-"void" function other than "main" that flows off the end by reaching the closing curly brace that terminates the function is undefined.
Unlike in C, in C++, flowing off the end of a non-"void" function other than "main" results in undefined behavior even when the value of the function is not used.
This warning is enabled by default in C++ and by -Wall otherwise.
switch ((int) (a == 4)) { ... }
This warning is enabled by default for C and C++ programs.
switch (cond) { i = 15; ... case 5: ... }
-Wswitch-unreachable does not warn if the statement between the controlling expression and the first case label is just a declaration:
switch (cond) { int i; ... case 5: i = 5; ... }
This warning is enabled by default for C and C++ programs.
To suppress this warning use the "unused" attribute.
This warning is also enabled by -Wunused together with -Wextra.
To suppress this warning use the "unused" attribute.
This warning is also enabled by -Wunused, which is enabled by -Wall.
To suppress this warning use the "unused" attribute.
To suppress this warning use the "unused" attribute.
To suppress this warning use the "unused" attribute.
To suppress this warning use the "unused" attribute.
This warning is enabled by -Wall.
In order to get a warning about an unused function parameter, you must either specify -Wextra -Wunused (note that -Wall implies -Wunused), or separately specify -Wunused-parameter.
If you want to warn about code that uses the uninitialized value of the variable in its own initializer, use the -Winit-self option.
These warnings occur for individual uninitialized or clobbered elements of structure, union or array variables as well as for variables that are uninitialized or clobbered as a whole. They do not occur for variables or elements declared "volatile". Because these warnings depend on optimization, the exact variables or elements for which there are warnings depends on the precise optimization options and version of GCC used.
Note that there may be no warning about a variable that is used only to compute a value that itself is never used, because such computations may be deleted by data flow analysis before the warnings are printed.
void store (int *i) { __atomic_store_n (i, 0, memory_order_consume); }
-Winvalid-memory-model is enabled by default.
These warnings are only possible in optimizing compilation, because otherwise GCC does not keep track of the state of variables.
These warnings are made optional because GCC may not be able to determine when the code is correct in spite of appearing to have an error. Here is one example of how this can happen:
{ int x; switch (y) { case 1: x = 1; break; case 2: x = 4; break; case 3: x = 5; } foo (x); }
If the value of "y" is always 1, 2 or 3, then "x" is always initialized, but GCC doesn't know this. To suppress the warning, you need to provide a default case with assert(0) or similar code.
This option also warns when a non-volatile automatic variable might be changed by a call to "longjmp". The compiler sees only the calls to "setjmp". It cannot know where "longjmp" will be called; in fact, a signal handler could call it at any point in the code. As a result, you may get a warning even when there is in fact no problem because "longjmp" cannot in fact be called at the place that would cause a problem.
Some spurious warnings can be avoided if you declare all the functions you use that never return as "noreturn".
This warning is enabled by -Wall or -Wextra.
Level 1: Most aggressive, quick, least accurate. Possibly useful when higher levels do not warn but -fstrict-aliasing still breaks the code, as it has very few false negatives. However, it has many false positives. Warns for all pointer conversions between possibly incompatible types, even if never dereferenced. Runs in the front end only.
Level 2: Aggressive, quick, not too precise. May still have many false positives (not as many as level 1 though), and few false negatives (but possibly more than level 1). Unlike level 1, it only warns when an address is taken. Warns about incomplete types. Runs in the front end only.
Level 3 (default for -Wstrict-aliasing): Should have very few false positives and few false negatives. Slightly slower than levels 1 or 2 when optimization is enabled. Takes care of the common pun+dereference pattern in the front end: "*(int*)&some_float". If optimization is enabled, it also runs in the back end, where it deals with multiple statement cases using flow-sensitive points-to information. Only warns when the converted pointer is dereferenced. Does not warn about incomplete types.
An optimization that assumes that signed overflow does not occur is perfectly safe if the values of the variables involved are such that overflow never does, in fact, occur. Therefore this warning can easily give a false positive: a warning about code that is not actually a problem. To help focus on important issues, several warning levels are defined. No warnings are issued for the use of undefined signed overflow when estimating how many iterations a loop requires, in particular when determining whether a loop will be executed at all.
enum Color { blue, purple, yellow }; const char* f (enum Color clr) { static char buf [4]; const char *str; switch (clr) { case blue: str = "blue"; break; case purple: str = "purple"; break; case yellow: str = "yellow"; break; } return strcpy (buf, str); // warning here }
Option -Wstringop-overflow=2 is enabled by default.
In the following example, the call to "strncat" specifies a bound that is less than the length of the source string. As a result, the copy of the source will be truncated and so the call is diagnosed. To avoid the warning use "bufsize - strlen (buf) - 1)" as the bound.
void append (char *buf, size_t bufsize) { strncat (buf, ".txt", 3); }
As another example, the following call to "strncpy" results in copying to "d" just the characters preceding the terminating NUL, without appending the NUL to the end. Assuming the result of "strncpy" is necessarily a NUL-terminated string is a common mistake, and so the call is diagnosed. To avoid the warning when the result is not expected to be NUL-terminated, call "memcpy" instead.
void copy (char *d, const char *s) { strncpy (d, s, strlen (s)); }
In the following example, the call to "strncpy" specifies the size of the destination buffer as the bound. If the length of the source string is equal to or greater than this size the result of the copy will not be NUL-terminated. Therefore, the call is also diagnosed. To avoid the warning, specify "sizeof buf - 1" as the bound and set the last element of the buffer to "NUL".
void copy (const char *s) { char buf[80]; strncpy (buf, s, sizeof buf); ... }
In situations where a character array is intended to store a sequence of bytes with no terminating "NUL" such an array may be annotated with attribute "nonstring" to avoid this warning. Such arrays, however, are not suitable arguments to functions that expect "NUL"-terminated strings. To help detect accidental misuses of such arrays GCC issues warnings unless it can prove that the use is safe.
GCC also warns about function definitions that might be candidates for "format" attributes. Again, these are only possible candidates. GCC guesses that "format" attributes might be appropriate for any function that calls a function like "vprintf" or "vscanf", but this might not always be the case, and some functions for which "format" attributes are appropriate may not be detected.
For example, a bounded case of "alloca" could be:
void func (size_t n) { void *p; if (n <= 1000) p = alloca (n); else p = malloc (n); f (p); }
In the above example, passing "-Walloca-larger-than=1000" would not issue a warning because the call to "alloca" is known to be at most 1000 bytes. However, if "-Walloca-larger-than=500" were passed, the compiler would emit a warning.
Unbounded uses, on the other hand, are uses of "alloca" with no controlling predicate constraining its integer argument. For example:
void func () { void *p = alloca (n); f (p); }
If "-Walloca-larger-than=500" were passed, the above would trigger a warning, but this time because of the lack of bounds checking.
Note, that even seemingly correct code involving signed integers could cause a warning:
void func (signed int n) { if (n < 500) { p = alloca (n); f (p); } }
In the above example, n could be negative, causing a larger than expected argument to be implicitly cast into the "alloca" call.
This option also warns when "alloca" is used in a loop.
-Walloca-larger-than=PTRDIFF_MAX is enabled by default but is usually only effective when -ftree-vrp is active (default for -O2 and above).
See also -Wvla-larger-than=byte-size.
Attributes considered include "alloc_align", "alloc_size", "cold", "const", "hot", "leaf", "malloc", "nonnull", "noreturn", "nothrow", "pure", "returns_nonnull", and "returns_twice".
-Wattribute-alias is equivalent to -Wattribute-alias=1. This is the default. You can disable these warnings with either -Wno-attribute-alias or -Wattribute-alias=0.
int n = 5; ... if ((n > 1) == 2) { ... }
This warning is enabled by -Wall.
This warning is enabled by -Wall.
if (p != NULL) return 0; else return 0;
It doesn't warn when both branches contain just a null statement. This warning also warn for conditional operators:
int i = x ? *p : *p;
if (p->q != NULL) { ... } else if (p->q != NULL) { ... }
int i = 1; ... if (i > i) { ... }
This warning also warns about bitwise comparisons that always evaluate to true or false, for instance:
if ((a & 16) == 10) { ... }
will always be false.
This warning is enabled by -Wall.
The idea behind this is that sometimes it is convenient (for the programmer) to consider floating-point values as approximations to infinitely precise real numbers. If you are doing this, then you need to compute (by analyzing the code, or in some other way) the maximum or likely maximum error that the computation introduces, and allow for it when performing comparisons (and when producing output, but that's a different problem). In particular, instead of testing for equality, you should check to see whether the two values have ranges that overlap; and this is done with the relational operators, so equality comparisons are probably mistaken.
for (SomeIterator i = SomeObj.begin(); i != SomeObj.end(); ++i) { for (int i = 0; i < N; ++i) { ... } ... }
Since the two variable "i" in the example above have incompatible types, enabling only -Wshadow=compatible-local will not emit a warning. Because their types are incompatible, if a programmer accidentally uses one in place of the other, type checking will catch that and emit an error or warning. So not warning (about shadowing) in this case will not lead to undetected bugs. Use of this flag instead of -Wshadow=local can possibly reduce the number of warnings triggered by intentional shadowing.
This warning is enabled by -Wshadow=local.
The message is in keeping with the output of -fstack-usage.
warning: stack usage is 1120 bytes
warning: stack usage might be 1648 bytes
warning: stack usage might be unbounded
-Wstack-usage=PTRDIFF_MAX is enabled by default. Warnings controlled by the option can be disabled either by specifying byte-size of SIZE_MAX or more or by -Wno-stack-usage.
Normally this only warns about global allocation functions, but -Waligned-new=all also warns about class member allocation functions.
char buf [64]; new (buf) int[64];
This warning is enabled by default.
struct S { int n, a[1]; }; S *s = (S *)malloc (sizeof *s + 31 * sizeof s->a[0]); new (s->a)int [32]();
struct S { int n, a[]; }; S *s = (S *)malloc (sizeof *s + 32 * sizeof s->a[0]); new (s->a)int [32]();
const char *p = foo (); if (p == '\0') return 42;
Note that the code above is invalid in C++11.
This warning is enabled by default.
This option is implied by -Wall. If -Wall is not given, this option is still enabled unless trigraphs are enabled. To get trigraph conversion without warnings, but get the other -Wall warnings, use -trigraphs -Wall -Wno-trigraphs.
Built-in macros, macros defined on the command line, and macros defined in include files are not warned about.
Note: If a macro is actually used, but only used in skipped conditional blocks, then the preprocessor reports it as unused. To avoid the warning in such a case, you might improve the scope of the macro's definition by, for example, moving it into the first skipped block. Alternatively, you could provide a dummy use with something like:
#if defined the_macro_causing_the_warning #endif
#if FOO ... #else FOO ... #endif FOO
The second and third "FOO" should be in comments. This warning is on by default.
Also warn when making a cast that introduces a type qualifier in an unsafe way. For example, casting "char **" to "const char **" is unsafe, as in this example:
/* p is char ** value. */ const char **q = (const char **) p; /* Assignment of readonly string to const char * is OK. */ *q = "string"; /* Now char** pointer points to read-only memory. */ **p = 'b';
When compiling C++, warn about the deprecated conversion from string literals to "char *". This warning is enabled by default for C++ programs.
For C++, also warn for confusing overload resolution for user-defined conversions; and conversions that never use a type conversion operator: conversions to "void", the same type, a base class or a reference to them. Warnings about conversions between signed and unsigned integers are disabled by default in C++ unless -Wsign-conversion is explicitly enabled.
{ if (a) if (b) foo (); else bar (); }
In C/C++, every "else" branch belongs to the innermost possible "if" statement, which in this example is "if (b)". This is often not what the programmer expected, as illustrated in the above example by indentation the programmer chose. When there is the potential for this confusion, GCC issues a warning when this flag is specified. To eliminate the warning, add explicit braces around the innermost "if" statement so there is no way the "else" can belong to the enclosing "if". The resulting code looks like this:
{ if (a) { if (b) foo (); else bar (); } }
This warning is enabled by -Wparentheses.
-Wjump-misses-init is included in -Wc++-compat. It can be disabled with the -Wno-jump-misses-init option.
void operator delete (void *) noexcept; void operator delete[] (void *) noexcept;
without a definition of the corresponding sized deallocation function
void operator delete (void *, std::size_t) noexcept; void operator delete[] (void *, std::size_t) noexcept;
or vice versa. Enabled by -Wextra along with -fsized-deallocation.
void make_file (const char *name) { char path[PATH_MAX]; strncpy (path, name, sizeof path - 1); strncat (path, ".text", sizeof ".text"); ... }
The -Wsizeof-pointer-memaccess option is enabled by -Wall.
extern int a; if (a < 0 && a < 0) { ... }
int a; ... if (!a > 1) { ... }
It is possible to suppress the warning by wrapping the LHS into parentheses:
if ((!a) > 1) { ... }
This warning is enabled by -Wall.
For example, the call to "memset" below is diagnosed by the warning because the function expects a value of type "size_t" as its argument but the type of 32 is "int". With -Wextra, the declaration of the function is diagnosed as well.
extern void* memset (); void f (void *d) { memset (d, '\0', 32); }
void foo(bar) { }
This warning is also enabled by -Wextra.
struct s { int f, g, h; }; struct s x = { 3, 4 };
This option does not warn about designated initializers, so the following modification does not trigger a warning:
struct s { int f, g, h; }; struct s x = { .f = 3, .g = 4 };
In C this option does not warn about the universal zero initializer { 0 }:
struct s { int f, g, h; }; struct s x = { 0 };
Likewise, in C++ this option does not warn about the empty { } initializer, for example:
struct s { int f, g, h; }; s x = { };
This warning is included in -Wextra. To get other -Wextra warnings without this one, use -Wextra -Wno-missing-field-initializers.
There are four levels of warning supported by GCC. The default is -Wnormalized=nfc, which warns about any identifier that is not in the ISO 10646 "C" normalized form, NFC. NFC is the recommended form for most uses. It is equivalent to -Wnormalized.
Unfortunately, there are some characters allowed in identifiers by ISO C and ISO C++ that, when turned into NFC, are not allowed in identifiers. That is, there's no way to use these symbols in portable ISO C or C++ and have all your identifiers in NFC. -Wnormalized=id suppresses the warning for these characters. It is hoped that future versions of the standards involved will correct this, which is why this option is not the default.
You can switch the warning off for all characters by writing -Wnormalized=none or -Wno-normalized. You should only do this if you are using some other normalization scheme (like "D"), because otherwise you can easily create bugs that are literally impossible to see.
Some characters in ISO 10646 have distinct meanings but look identical in some fonts or display methodologies, especially once formatting has been applied. For instance "\u207F", "SUPERSCRIPT LATIN SMALL LETTER N", displays just like a regular "n" that has been placed in a superscript. ISO 10646 defines the NFKC normalization scheme to convert all these into a standard form as well, and GCC warns if your code is not in NFKC if you use -Wnormalized=nfkc. This warning is comparable to warning about every identifier that contains the letter O because it might be confused with the digit 0, and so is not the default, but may be useful as a local coding convention if the programming environment cannot be fixed to display these characters distinctly.
This warning is included in -Wextra. To get other -Wextra warnings without this one, use -Wextra -Wno-override-init.
struct foo { int x; char a, b, c, d; } __attribute__((packed)); struct bar { char z; struct foo f; };
struct foo { char a:4; char b:8; } __attribute__ ((packed));
This warning is enabled by default. Use -Wno-packed-bitfield-compat to disable this warning.
struct __attribute__ ((aligned (8))) S8 { char a[8]; }; struct __attribute__ ((packed)) S { struct S8 s8; };
This warning is enabled by -Wall.
void foo (void) { char a[] = "abcd1234"; strcpy (a, a + 4); ... }
The -Wrestrict option detects some instances of simple overlap even without optimization but works best at -O2 and above. It is included in -Wall.
The compiler uses a variety of heuristics to determine whether or not to inline a function. For example, the compiler takes into account the size of the function being inlined and the amount of inlining that has already been done in the current function. Therefore, seemingly insignificant changes in the source program can cause the warnings produced by -Winline to appear or disappear.
The restrictions on "offsetof" may be relaxed in a future version of the C++ standard.
Note that GCC may optimize small variable-length arrays of a known value into plain arrays, so this warning may not get triggered for such arrays.
-Wvla-larger-than=PTRDIFF_MAX is enabled by default but is typically only effective when -ftree-vrp is active (default for -O2 and above).
See also -Walloca-larger-than=byte-size.
The limit applies after string constant concatenation, and does not count the trailing NUL. In C90, the limit was 509 characters; in C99, it was raised to 4095. C++98 does not specify a normative minimum maximum, so we do not diagnose overlength strings in C++.
This option is implied by -Wpedantic, and can be disabled with -Wno-overlength-strings.
GCC allows you to use -g with -O. The shortcuts taken by optimized code may occasionally be surprising: some variables you declared may not exist at all; flow of control may briefly move where you did not expect it; some statements may not be executed because they compute constant results or their values are already at hand; some statements may execute in different places because they have been moved out of loops. Nevertheless it is possible to debug optimized output. This makes it reasonable to use the optimizer for programs that might have bugs.
If you are not using some other optimization option, consider using -Og with -g. With no -O option at all, some compiler passes that collect information useful for debugging do not run at all, so that -Og may result in a better debugging experience.
On most systems that use stabs format, -g enables use of extra debugging information that only GDB can use; this extra information makes debugging work better in GDB but probably makes other debuggers crash or refuse to read the program. If you want to control for certain whether to generate the extra information, use -gstabs+, -gstabs, -gxcoff+, -gxcoff, or -gvms (see below).
Note that with DWARF Version 2, some ports require and always use some non-conflicting DWARF 3 extensions in the unwind tables.
Version 4 may require GDB 7.0 and -fvar-tracking-assignments for maximum benefit.
GCC no longer supports DWARF Version 1, which is substantially different than Version 2 and later. For historical reasons, some other DWARF-related options such as -fno-dwarf2-cfi-asm) retain a reference to DWARF Version 2 in their names, but apply to all currently-supported versions of DWARF.
Level 0 produces no debug information at all. Thus, -g0 negates -g.
Level 1 produces minimal information, enough for making backtraces in parts of the program that you don't plan to debug. This includes descriptions of functions and external variables, and line number tables, but no information about local variables.
Level 3 includes extra information, such as all the macro definitions present in the program. Some debuggers support macro expansion when you use -g3.
If you use multiple -g options, with or without level numbers, the last such option is the one that is effective.
-gdwarf does not accept a concatenated debug level, to avoid confusion with -gdwarf-level. Instead use an additional -glevel option to change the debug level for DWARF.
It is enabled by default when compiling with optimization (-Os, -O, -O2, ...), debugging information (-g) and the debug info format supports it.
It can be enabled even if var-tracking is disabled, in which case annotations are created and maintained, but discarded at the end. By default, this flag is enabled together with -fvar-tracking, except when selective scheduling is enabled.
This is generally desirable, because assembler-generated line-number tables are a lot more compact than those the compiler can generate itself.
This option will be enabled by default if, at GCC configure time, the assembler was found to support such directives.
This option will be enabled by default if, at GCC configure time, the assembler was found to support them.
This is enabled by default when outputting DWARF 2 debug information at the normal level, as long as there is assembler support, -fvar-tracking-assignments is enabled and -gstrict-dwarf is not. When assembler support is not available, this may still be enabled, but it will force GCC to output internal line number tables, and if -ginternal-reset-location-views is not enabled, that will most certainly lead to silently mismatching location views.
There is a proposed representation for view numbers that is not backward compatible with the location list format introduced in DWARF 5, that can be enabled with -gvariable-location-views=incompat5. This option may be removed in the future, is only provided as a reference implementation of the proposed representation. Debug information consumers are not expected to support this extended format, and they would be rendered unable to decode location lists using it.
This option substantially reduces the size of debugging information, but at significant potential loss in type information to the debugger. See -femit-struct-debug-reduced for a less aggressive option. See -femit-struct-debug-detailed for more detailed control.
This option works only with DWARF debug output.
This option significantly reduces the size of debugging information, with some potential loss in type information to the debugger. See -femit-struct-debug-baseonly for a more aggressive option. See -femit-struct-debug-detailed for more detailed control.
This option works only with DWARF debug output.
This option is a detailed version of -femit-struct-debug-reduced and -femit-struct-debug-baseonly, which serves for most needs.
A specification has the syntax[dir:|ind:][ord:|gen:](any|sys|base|none)
The optional first word limits the specification to structs that are used directly (dir:) or used indirectly (ind:). A struct type is used directly when it is the type of a variable, member. Indirect uses arise through pointers to structs. That is, when use of an incomplete struct is valid, the use is indirect. An example is struct one direct; struct two * indirect;.
The optional second word limits the specification to ordinary structs (ord:) or generic structs (gen:). Generic structs are a bit complicated to explain. For C++, these are non-explicit specializations of template classes, or non-template classes within the above. Other programming languages have generics, but -femit-struct-debug-detailed does not yet implement them.
The third word specifies the source files for those structs for which the compiler should emit debug information. The values none and any have the normal meaning. The value base means that the base of name of the file in which the type declaration appears must match the base of the name of the main compilation file. In practice, this means that when compiling foo.c, debug information is generated for types declared in that file and foo.h, but not other header files. The value sys means those types satisfying base or declared in system or compiler headers.
You may need to experiment to determine the best settings for your application.
The default is -femit-struct-debug-detailed=all.
This option works only with DWARF debug output.
Without any optimization option, the compiler's goal is to reduce the cost of compilation and to make debugging produce the expected results. Statements are independent: if you stop the program with a breakpoint between statements, you can then assign a new value to any variable or change the program counter to any other statement in the function and get exactly the results you expect from the source code.
Turning on optimization flags makes the compiler attempt to improve the performance and/or code size at the expense of compilation time and possibly the ability to debug the program.
The compiler performs optimization based on the knowledge it has of the program. Compiling multiple files at once to a single output file mode allows the compiler to use information gained from all of the files when compiling each of them.
Not all optimizations are controlled directly by a flag. Only optimizations that have a flag are listed in this section.
Most optimizations are completely disabled at -O0 or if an -O level is not set on the command line, even if individual optimization flags are specified. Similarly, -Og suppresses many optimization passes.
Depending on the target and how GCC was configured, a slightly different set of optimizations may be enabled at each -O level than those listed here. You can invoke GCC with -Q --help=optimizers to find out the exact set of optimizations that are enabled at each level.
With -O, the compiler tries to reduce code size and execution time, without performing any optimizations that take a great deal of compilation time.
-O turns on the following optimization flags:
-fauto-inc-dec -fbranch-count-reg -fcombine-stack-adjustments -fcompare-elim -fcprop-registers -fdce -fdefer-pop -fdelayed-branch -fdse -fforward-propagate -fguess-branch-probability -fif-conversion -fif-conversion2 -finline-functions-called-once -fipa-profile -fipa-pure-const -fipa-reference -fipa-reference-addressable -fmerge-constants -fmove-loop-invariants -fomit-frame-pointer -freorder-blocks -fshrink-wrap -fshrink-wrap-separate -fsplit-wide-types -fssa-backprop -fssa-phiopt -ftree-bit-ccp -ftree-ccp -ftree-ch -ftree-coalesce-vars -ftree-copy-prop -ftree-dce -ftree-dominator-opts -ftree-dse -ftree-forwprop -ftree-fre -ftree-phiprop -ftree-pta -ftree-scev-cprop -ftree-sink -ftree-slsr -ftree-sra -ftree-ter -funit-at-a-time
-O2 turns on all optimization flags specified by -O. It also turns on the following optimization flags:
-falign-functions -falign-jumps -falign-labels -falign-loops -fcaller-saves -fcode-hoisting -fcrossjumping -fcse-follow-jumps -fcse-skip-blocks -fdelete-null-pointer-checks -fdevirtualize -fdevirtualize-speculatively -fexpensive-optimizations -fgcse -fgcse-lm -fhoist-adjacent-loads -finline-small-functions -findirect-inlining -fipa-bit-cp -fipa-cp -fipa-icf -fipa-ra -fipa-sra -fipa-vrp -fisolate-erroneous-paths-dereference -flra-remat -foptimize-sibling-calls -foptimize-strlen -fpartial-inlining -fpeephole2 -freorder-blocks-algorithm=stc -freorder-blocks-and-partition -freorder-functions -frerun-cse-after-loop -fschedule-insns -fschedule-insns2 -fsched-interblock -fsched-spec -fstore-merging -fstrict-aliasing -fthread-jumps -ftree-builtin-call-dce -ftree-pre -ftree-switch-conversion -ftree-tail-merge -ftree-vrp
Please note the warning under -fgcse about invoking -O2 on programs that use computed gotos.
NOTE: In Alpine Linux, -D_FORTIFY_SOURCE=2 is set by default, and is activated when -O is set to 2 or higher. This enables additional compile-time and run-time checks for several libc functions. To disable, specify either -U_FORTIFY_SOURCE or -D_FORTIFY_SOURCE=0.
-fgcse-after-reload -finline-functions -fipa-cp-clone -floop-interchange -floop-unroll-and-jam -fpeel-loops -fpredictive-commoning -fsplit-paths -ftree-loop-distribute-patterns -ftree-loop-distribution -ftree-loop-vectorize -ftree-partial-pre -ftree-slp-vectorize -funswitch-loops -fvect-cost-model -fversion-loops-for-strides
-falign-functions -falign-jumps -falign-labels -falign-loops -fprefetch-loop-arrays -freorder-blocks-algorithm=stc
It also enables -finline-functions, causes the compiler to tune for code size rather than execution speed, and performs further optimizations designed to reduce code size.
Like -O0, -Og completely disables a number of optimization passes so that individual options controlling them have no effect. Otherwise -Og enables all -O1 optimization flags except for those that may interfere with debugging:
-fbranch-count-reg -fdelayed-branch -fif-conversion -fif-conversion2 -finline-functions-called-once -fmove-loop-invariants -fssa-phiopt -ftree-bit-ccp -ftree-pta -ftree-sra
If you use multiple -O options, with or without level numbers, the last such option is the one that is effective.
Options of the form -fflag specify machine-independent flags. Most flags have both positive and negative forms; the negative form of -ffoo is -fno-foo. In the table below, only one of the forms is listed---the one you typically use. You can figure out the other form by either removing no- or adding it.
The following options control specific optimizations. They are either activated by -O options or are related to ones that are. You can use the following flags in the rare cases when "fine-tuning" of optimizations to be performed is desired.
This option is enabled by default at optimization levels -O, -O2, -O3, -Os.
The default is -ffp-contract=fast.
On some targets this flag has no effect because the standard calling sequence always uses a frame pointer, so it cannot be omitted.
Note that -fno-omit-frame-pointer doesn't guarantee the frame pointer is used in all functions. Several targets always omit the frame pointer in leaf functions.
Enabled by default at -O and higher.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O2, -O3.
Single functions can be exempted from inlining by marking them with the "noinline" attribute.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O2, -O3, -Os.
If all calls to a given function are integrated, and the function is declared "static", then the function is normally not output as assembler code in its own right.
Enabled at levels -O3, -Os. Also enabled by -fprofile-use and -fauto-profile.
Enabled at levels -O1, -O2, -O3 and -Os, but not -Og.
Enabled by default.
Enabled at levels -O2, -O3 and -Os.
Inlining is actually controlled by a number of parameters, which may be specified individually by using --param name=value. The -finline-limit=n option sets some of these parameters as follows:
See below for a documentation of the individual parameters controlling inlining and for the defaults of these parameters.
Note: there may be no value to -finline-limit that results in default behavior.
Note: pseudo instruction represents, in this particular context, an abstract measurement of function's size. In no way does it represent a count of assembly instructions and as such its exact meaning might change from one release to an another.
GCC enables this option by default. If you want to force the compiler to check if a variable is referenced, regardless of whether or not optimization is turned on, use the -fno-keep-static-consts option.
This option is the default for optimized compilation if the assembler and linker support it. Use -fno-merge-constants to inhibit this behavior.
Enabled at levels -O, -O2, -O3, -Os.
This option implies -fmerge-constants. In addition to -fmerge-constants this considers e.g. even constant initialized arrays or initialized constant variables with integral or floating-point types. Languages like C or C++ require each variable, including multiple instances of the same variable in recursive calls, to have distinct locations, so using this option results in non-conforming behavior.
The default is -fbranch-count-reg at -O1 and higher, except for -Og.
This option results in less efficient code, but some strange hacks that alter the assembler output may be confused by the optimizations performed when this option is not used.
The default is -ffunction-cse
This option turns off this behavior because some programs explicitly rely on variables going to the data section---e.g., so that the resulting executable can find the beginning of that section and/or make assumptions based on that.
The default is -fzero-initialized-in-bss.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O, -O2, -O3, -Os.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O2, -O3, -Os.
Note: When compiling a program using computed gotos, a GCC extension, you may get better run-time performance if you disable the global common subexpression elimination pass by adding -fno-gcse to the command line.
Enabled at levels -O2, -O3, -Os.
Enabled by default when -fgcse is enabled.
Not enabled at any optimization level.
Not enabled at any optimization level.
Enabled by -fprofile-use and -fauto-profile.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O, -O2, -O3, -Os, but not with -Og.
Enabled at levels -O, -O2, -O3, -Os, but not with -Og.
Enabled by -Os.
Note however that in some environments this assumption is not true. Use -fno-delete-null-pointer-checks to disable this optimization for programs that depend on that behavior.
This option is enabled by default on most targets. On Nios II ELF, it defaults to off. On AVR, CR16, and MSP430, this option is completely disabled.
Passes that use the dataflow information are enabled independently at different optimization levels.
Enabled at levels -O2, -O3, -Os.
Enabled for Alpha, AArch64 and x86 at levels -O2, -O3, -Os.
This option is enabled at level -Os for all targets.
This option is enabled at level -O3 for some targets.
Enabled at levels -O2, -O3, -Os.
Enabled at levels -O, -O2, -O3, -Os, but not at -Og.
Enabled at levels -O2, -O3.
Enabled at levels -O2, -O3, -Os.
This only makes sense when scheduling after register allocation, i.e. with -fschedule-insns2 or at -O2 or higher.
This option is always enabled by default on certain machines, usually those which have no call-preserved registers to use instead.
Enabled at levels -O2, -O3, -Os.
Enabled by default at -O1 and higher.
Enabled at levels -O2, -O3, -Os, however the option is disabled if generated code will be instrumented for profiling (-p, or -pg) or if callee's register usage cannot be known exactly (this happens on targets that do not expose prologues and epilogues in RTL).
Although the behavior is similar to the Gold Linker's ICF optimization, GCC ICF works on different levels and thus the optimizations are not same - there are equivalences that are found only by GCC and equivalences found only by Gold.
This flag is enabled by default at -O2 and -Os.
If the compiler's optimization uses a function's body or information extracted from its body to optimize/change another function, the latter is called an impacted function of the former. If a function is patched, its impacted functions should be patched too.
The impacted functions are determined by the compiler's interprocedural optimizations. For example, a caller is impacted when inlining a function into its caller, cloning a function and changing its caller to call this new clone, or extracting a function's pureness/constness information to optimize its direct or indirect callers, etc.
Usually, the more IPA optimizations enabled, the larger the number of impacted functions for each function. In order to control the number of impacted functions and more easily compute the list of impacted function, IPA optimizations can be partially enabled at two different levels.
The level argument should be one of the following:
-flive-patching=inline-clone disables the following optimization flags: -fwhole-program -fipa-pta -fipa-reference -fipa-ra -fipa-icf -fipa-icf-functions -fipa-icf-variables -fipa-bit-cp -fipa-vrp -fipa-pure-const -fipa-reference-addressable -fipa-stack-alignment
In addition to all the flags that -flive-patching=inline-clone disables, -flive-patching=inline-only-static disables the following additional optimization flags: -fipa-cp-clone -fipa-sra -fpartial-inlining -fipa-cp
When -flive-patching is specified without any value, the default value is inline-clone.
This flag is disabled by default.
Note that -flive-patching is not supported with link-time optimization (-flto).
DO I = 1, N A(I) = B(I) + C D(I) = E(I) * F ENDDO
is transformed to
DO I = 1, N A(I) = B(I) + C ENDDO DO I = 1, N D(I) = E(I) * F ENDDO
This flag is enabled by default at -O3. It is also enabled by -fprofile-use and -fauto-profile.
This pass distributes the initialization loops and generates a call to memset zero. For example, the loop
DO I = 1, N A(I) = 0 B(I) = A(I) + I ENDDO
is transformed to
DO I = 1, N A(I) = 0 ENDDO DO I = 1, N B(I) = A(I) + I ENDDO
and the initialization loop is transformed into a call to memset zero. This flag is enabled by default at -O3. It is also enabled by -fprofile-use and -fauto-profile.
for (int i = 0; i < N; i++) for (int j = 0; j < N; j++) for (int k = 0; k < N; k++) c[i][j] = c[i][j] + a[i][k]*b[k][j];
is transformed to
for (int i = 0; i < N; i++) for (int k = 0; k < N; k++) for (int j = 0; j < N; j++) c[i][j] = c[i][j] + a[i][k]*b[k][j];
This flag is enabled by default at -O3. It is also enabled by -fprofile-use and -fauto-profile.
A combination of -fweb and CSE is often sufficient to obtain the same effect. However, that is not reliable in cases where the loop body is more complicated than a single basic block. It also does not work at all on some architectures due to restrictions in the CSE pass.
This optimization is enabled by default.
Enabled at levels -O2, -O3, -Os.
This option is enabled at level -O3. It is also enabled by -fprofile-use and -fauto-profile.
This option may generate better or worse code; results are highly dependent on the structure of loops within the source code.
Disabled at level -Os.
char buf[9]; if (snprintf (buf, "%08x", i) >= sizeof buf) ...
The -fprintf-return-value option relies on other optimizations and yields best results with -O2 and above. It works in tandem with the -Wformat-overflow and -Wformat-truncation options. The -fprintf-return-value option is enabled by default.
-fpeephole is enabled by default. -fpeephole2 enabled at levels -O2, -O3, -Os.
GCC uses heuristics to guess branch probabilities if they are not provided by profiling feedback (-fprofile-arcs). These heuristics are based on the control flow graph. If some branch probabilities are specified by "__builtin_expect", then the heuristics are used to guess branch probabilities for the rest of the control flow graph, taking the "__builtin_expect" info into account. The interactions between the heuristics and "__builtin_expect" can be complex, and in some cases, it may be useful to disable the heuristics so that the effects of "__builtin_expect" are easier to understand.
It is also possible to specify expected probability of the expression with "__builtin_expect_with_probability" built-in function.
The default is -fguess-branch-probability at levels -O, -O2, -O3, -Os.
Enabled at levels -O, -O2, -O3, -Os.
The default is simple at levels -O, -Os, and stc at levels -O2, -O3.
This optimization is automatically turned off in the presence of exception handling or unwind tables (on targets using setjump/longjump or target specific scheme), for linkonce sections, for functions with a user-defined section attribute and on any architecture that does not support named sections. When -fsplit-stack is used this option is not enabled by default (to avoid linker errors), but may be enabled explicitly (if using a working linker).
Enabled for x86 at levels -O2, -O3, -Os.
This option isn't effective unless you either provide profile feedback (see -fprofile-arcs for details) or manually annotate functions with "hot" or "cold" attributes.
Enabled at levels -O2, -O3, -Os.
Pay special attention to code like this:
union a_union { int i; double d; }; int f() { union a_union t; t.d = 3.0; return t.i; }
The practice of reading from a different union member than the one most recently written to (called "type-punning") is common. Even with -fstrict-aliasing, type-punning is allowed, provided the memory is accessed through the union type. So, the code above works as expected. However, this code might not:
int f() { union a_union t; int* ip; t.d = 3.0; ip = &t.i; return *ip; }
Similarly, access by taking the address, casting the resulting pointer and dereferencing the result has undefined behavior, even if the cast uses a union type, e.g.:
int f() { double d = 3.0; return ((union a_union *) &d)->i; }
The -fstrict-aliasing option is enabled at levels -O2, -O3, -Os.
If m is not specified, it defaults to n.
Examples: -falign-functions=32 aligns functions to the next 32-byte boundary, -falign-functions=24 aligns to the next 32-byte boundary only if this can be done by skipping 23 bytes or less, -falign-functions=32:7 aligns to the next 32-byte boundary only if this can be done by skipping 6 bytes or less.
The second pair of n2:m2 values allows you to specify a secondary alignment: -falign-functions=64:7:32:3 aligns to the next 64-byte boundary if this can be done by skipping 6 bytes or less, otherwise aligns to the next 32-byte boundary if this can be done by skipping 2 bytes or less. If m2 is not specified, it defaults to n2.
Some assemblers only support this flag when n is a power of two; in that case, it is rounded up.
-fno-align-functions and -falign-functions=1 are equivalent and mean that functions are not aligned.
If n is not specified or is zero, use a machine-dependent default. The maximum allowed n option value is 65536.
Enabled at levels -O2, -O3.
Parameters of this option are analogous to the -falign-functions option. -fno-align-labels and -falign-labels=1 are equivalent and mean that labels are not aligned.
If -falign-loops or -falign-jumps are applicable and are greater than this value, then their values are used instead.
If n is not specified or is zero, use a machine-dependent default which is very likely to be 1, meaning no alignment. The maximum allowed n option value is 65536.
Enabled at levels -O2, -O3.
Parameters of this option are analogous to the -falign-functions option. -fno-align-loops and -falign-loops=1 are equivalent and mean that loops are not aligned. The maximum allowed n option value is 65536.
If n is not specified or is zero, use a machine-dependent default.
Enabled at levels -O2, -O3.
Parameters of this option are analogous to the -falign-functions option. -fno-align-jumps and -falign-jumps=1 are equivalent and mean that loops are not aligned.
If n is not specified or is zero, use a machine-dependent default. The maximum allowed n option value is 65536.
Enabled at levels -O2, -O3.
Enabled by default.
-ftoplevel-reorder is the default at -O1 and higher, and also at -O0 if -fsection-anchors is explicitly requested. Additionally -fno-toplevel-reorder implies -fno-section-anchors.
Enabled by default with -funroll-loops.
This option should not be used in combination with -flto. Instead relying on a linker plugin should provide safer and more precise information.
To use the link-time optimizer, -flto and optimization options should be specified at compile time and during the final link. It is recommended that you compile all the files participating in the same link with the same options and also specify those options at link time. For example:
gcc -c -O2 -flto foo.c gcc -c -O2 -flto bar.c gcc -o myprog -flto -O2 foo.o bar.o
The first two invocations to GCC save a bytecode representation of GIMPLE into special ELF sections inside foo.o and bar.o. The final invocation reads the GIMPLE bytecode from foo.o and bar.o, merges the two files into a single internal image, and compiles the result as usual. Since both foo.o and bar.o are merged into a single image, this causes all the interprocedural analyses and optimizations in GCC to work across the two files as if they were a single one. This means, for example, that the inliner is able to inline functions in bar.o into functions in foo.o and vice-versa.
Another (simpler) way to enable link-time optimization is:
gcc -o myprog -flto -O2 foo.c bar.c
The above generates bytecode for foo.c and bar.c, merges them together into a single GIMPLE representation and optimizes them as usual to produce myprog.
The important thing to keep in mind is that to enable link-time optimizations you need to use the GCC driver to perform the link step. GCC automatically performs link-time optimization if any of the objects involved were compiled with the -flto command-line option. You can always override the automatic decision to do link-time optimization by passing -fno-lto to the link command.
To make whole program optimization effective, it is necessary to make certain whole program assumptions. The compiler needs to know what functions and variables can be accessed by libraries and runtime outside of the link-time optimized unit. When supported by the linker, the linker plugin (see -fuse-linker-plugin) passes information to the compiler about used and externally visible symbols. When the linker plugin is not available, -fwhole-program should be used to allow the compiler to make these assumptions, which leads to more aggressive optimization decisions.
When a file is compiled with -flto without -fuse-linker-plugin, the generated object file is larger than a regular object file because it contains GIMPLE bytecodes and the usual final code (see -ffat-lto-objects. This means that object files with LTO information can be linked as normal object files; if -fno-lto is passed to the linker, no interprocedural optimizations are applied. Note that when -fno-fat-lto-objects is enabled the compile stage is faster but you cannot perform a regular, non-LTO link on them.
When producing the final binary, GCC only applies link-time optimizations to those files that contain bytecode. Therefore, you can mix and match object files and libraries with GIMPLE bytecodes and final object code. GCC automatically selects which files to optimize in LTO mode and which files to link without further processing.
Generally, options specified at link time override those specified at compile time, although in some cases GCC attempts to infer link-time options from the settings used to compile the input files.
If you do not specify an optimization level option -O at link time, then GCC uses the highest optimization level used when compiling the object files. Note that it is generally ineffective to specify an optimization level option only at link time and not at compile time, for two reasons. First, compiling without optimization suppresses compiler passes that gather information needed for effective optimization at link time. Second, some early optimization passes can be performed only at compile time and not at link time.
There are some code generation flags preserved by GCC when generating bytecodes, as they need to be used during the final link. Currently, the following options and their settings are taken from the first object file that explicitly specifies them: -fPIC, -fpic, -fpie, -fcommon, -fexceptions, -fnon-call-exceptions, -fgnu-tm and all the -m target flags.
Certain ABI-changing flags are required to match in all compilation units, and trying to override this at link time with a conflicting value is ignored. This includes options such as -freg-struct-return and -fpcc-struct-return.
Other options such as -ffp-contract, -fno-strict-overflow, -fwrapv, -fno-trapv or -fno-strict-aliasing are passed through to the link stage and merged conservatively for conflicting translation units. Specifically -fno-strict-overflow, -fwrapv and -fno-trapv take precedence; and for example -ffp-contract=off takes precedence over -ffp-contract=fast. You can override them at link time.
If LTO encounters objects with C linkage declared with incompatible types in separate translation units to be linked together (undefined behavior according to ISO C99 6.2.7), a non-fatal diagnostic may be issued. The behavior is still undefined at run time. Similar diagnostics may be raised for other languages.
Another feature of LTO is that it is possible to apply interprocedural optimizations on files written in different languages:
gcc -c -flto foo.c g++ -c -flto bar.cc gfortran -c -flto baz.f90 g++ -o myprog -flto -O3 foo.o bar.o baz.o -lgfortran
Notice that the final link is done with g++ to get the C++ runtime libraries and -lgfortran is added to get the Fortran runtime libraries. In general, when mixing languages in LTO mode, you should use the same link command options as when mixing languages in a regular (non-LTO) compilation.
If object files containing GIMPLE bytecode are stored in a library archive, say libfoo.a, it is possible to extract and use them in an LTO link if you are using a linker with plugin support. To create static libraries suitable for LTO, use gcc-ar and gcc-ranlib instead of ar and ranlib; to show the symbols of object files with GIMPLE bytecode, use gcc-nm. Those commands require that ar, ranlib and nm have been compiled with plugin support. At link time, use the flag -fuse-linker-plugin to ensure that the library participates in the LTO optimization process:
gcc -o myprog -O2 -flto -fuse-linker-plugin a.o b.o -lfoo
With the linker plugin enabled, the linker extracts the needed GIMPLE files from libfoo.a and passes them on to the running GCC to make them part of the aggregated GIMPLE image to be optimized.
If you are not using a linker with plugin support and/or do not enable the linker plugin, then the objects inside libfoo.a are extracted and linked as usual, but they do not participate in the LTO optimization process. In order to make a static library suitable for both LTO optimization and usual linkage, compile its object files with -flto -ffat-lto-objects.
Link-time optimizations do not require the presence of the whole program to operate. If the program does not require any symbols to be exported, it is possible to combine -flto and -fwhole-program to allow the interprocedural optimizers to use more aggressive assumptions which may lead to improved optimization opportunities. Use of -fwhole-program is not needed when linker plugin is active (see -fuse-linker-plugin).
The current implementation of LTO makes no attempt to generate bytecode that is portable between different types of hosts. The bytecode files are versioned and there is a strict version check, so bytecode files generated in one version of GCC do not work with an older or newer version of GCC.
Link-time optimization does not work well with generation of debugging information on systems other than those using a combination of ELF and DWARF.
If you specify the optional n, the optimization and code generation done at link time is executed in parallel using n parallel jobs by utilizing an installed make program. The environment variable MAKE may be used to override the program used. The default value for n is 1.
You can also specify -flto=jobserver to use GNU make's job server mode to determine the number of parallel jobs. This is useful when the Makefile calling GCC is already executing in parallel. You must prepend a + to the command recipe in the parent Makefile for this to work. This option likely only works if MAKE is GNU make.
This option enables the extraction of object files with GIMPLE bytecode out of library archives. This improves the quality of optimization by exposing more code to the link-time optimizer. This information specifies what symbols can be accessed externally (by non-LTO object or during dynamic linking). Resulting code quality improvements on binaries (and shared libraries that use hidden visibility) are similar to -fwhole-program. See -flto for a description of the effect of this flag and how to use it.
This option is enabled by default when LTO support in GCC is enabled and GCC was configured for use with a linker supporting plugins (GNU ld 2.21 or newer or gold).
-fno-fat-lto-objects improves compilation time over plain LTO, but requires the complete toolchain to be aware of LTO. It requires a linker with linker plugin support for basic functionality. Additionally, nm, ar and ranlib need to support linker plugins to allow a full-featured build environment (capable of building static libraries etc). GCC provides the gcc-ar, gcc-nm, gcc-ranlib wrappers to pass the right options to these tools. With non fat LTO makefiles need to be modified to use them.
Note that modern binutils provide plugin auto-load mechanism. Installing the linker plugin into $libdir/bfd-plugins has the same effect as usage of the command wrappers (gcc-ar, gcc-nm and gcc-ranlib).
The default is -fno-fat-lto-objects on targets with linker plugin support.
This pass only applies to certain targets that cannot explicitly represent the comparison operation before register allocation is complete.
Enabled at levels -O, -O2, -O3, -Os.
Enabled at levels -O, -O2, -O3, -Os.
This option is enabled by -fauto-profile.
-fbranch-probabilities -fprofile-values -funroll-loops -fpeel-loops -ftracer -fvpt -finline-functions -fipa-cp -fipa-cp-clone -fipa-bit-cp -fpredictive-commoning -fsplit-loops -funswitch-loops -fgcse-after-reload -ftree-loop-vectorize -ftree-slp-vectorize -fvect-cost-model=dynamic -ftree-loop-distribute-patterns -fprofile-reorder-functions
Before you can use this option, you must first generate profiling information.
By default, GCC emits an error message if the feedback profiles do not match the source code. This error can be turned into a warning by using -Wno-error=coverage-mismatch. Note this may result in poorly optimized code. Additionally, by default, GCC also emits a warning message if the feedback profiles do not exist (see -Wmissing-profile).
If path is specified, GCC looks at the path to find the profile feedback data files. See -fprofile-dir.
-fbranch-probabilities -fprofile-values -funroll-loops -fpeel-loops -ftracer -fvpt -finline-functions -fipa-cp -fipa-cp-clone -fipa-bit-cp -fpredictive-commoning -fsplit-loops -funswitch-loops -fgcse-after-reload -ftree-loop-vectorize -ftree-slp-vectorize -fvect-cost-model=dynamic -ftree-loop-distribute-patterns -fprofile-correction
path is the name of a file containing AutoFDO profile information. If omitted, it defaults to fbdata.afdo in the current directory.
Producing an AutoFDO profile data file requires running your program with the perf utility on a supported GNU/Linux target system. For more information, see <https://perf.wiki.kernel.org/>.
E.g.
perf record -e br_inst_retired:near_taken -b -o perf.data \ -- your_program
Then use the create_gcov tool to convert the raw profile data to a format that can be used by GCC. You must also supply the unstripped binary for your program to this tool. See <https://github.com/google/autofdo>.
E.g.
create_gcov --binary=your_program.unstripped --profile=perf.data \ --gcov=profile.afdo
The following options control compiler behavior regarding floating-point arithmetic. These options trade off between speed and correctness. All must be specifically enabled.
This option prevents undesirable excess precision on machines such as the 68000 where the floating registers (of the 68881) keep more precision than a "double" is supposed to have. Similarly for the x86 architecture. For most programs, the excess precision does only good, but a few programs rely on the precise definition of IEEE floating point. Use -ffloat-store for such programs, after modifying them to store all pertinent intermediate computations into variables.
-fexcess-precision=standard is not implemented for languages other than C. On the x86, it has no effect if -mfpmath=sse or -mfpmath=sse+387 is specified; in the former case, IEEE semantics apply without excess precision, and in the latter, rounding is unpredictable.
This option causes the preprocessor macro "__FAST_MATH__" to be defined.
This option is not turned on by any -O option besides -Ofast since it can result in incorrect output for programs that depend on an exact implementation of IEEE or ISO rules/specifications for math functions. It may, however, yield faster code for programs that do not require the guarantees of these specifications.
This option is not turned on by any -O option since it can result in incorrect output for programs that depend on an exact implementation of IEEE or ISO rules/specifications for math functions. It may, however, yield faster code for programs that do not require the guarantees of these specifications.
The default is -fmath-errno.
On Darwin systems, the math library never sets "errno". There is therefore no reason for the compiler to consider the possibility that it might, and -fno-math-errno is the default.
This option is not turned on by any -O option since it can result in incorrect output for programs that depend on an exact implementation of IEEE or ISO rules/specifications for math functions. It may, however, yield faster code for programs that do not require the guarantees of these specifications. Enables -fno-signed-zeros, -fno-trapping-math, -fassociative-math and -freciprocal-math.
The default is -fno-unsafe-math-optimizations.
The default is -fno-associative-math.
The default is -fno-reciprocal-math.
This option is not turned on by any -O option since it can result in incorrect output for programs that depend on an exact implementation of IEEE or ISO rules/specifications for math functions. It may, however, yield faster code for programs that do not require the guarantees of these specifications.
The default is -fno-finite-math-only.
The default is -fsigned-zeros.
This option should never be turned on by any -O option since it can result in incorrect output for programs that depend on an exact implementation of IEEE or ISO rules/specifications for math functions.
The default is -ftrapping-math.
The default is -fno-rounding-math.
This option is experimental and does not currently guarantee to disable all GCC optimizations that are affected by rounding mode. Future versions of GCC may provide finer control of this setting using C99's "FENV_ACCESS" pragma. This command-line option will be used to specify the default state for "FENV_ACCESS".
This option causes the preprocessor macro "__SUPPORT_SNAN__" to be defined.
The default is -fno-signaling-nans.
This option is experimental and does not currently guarantee to disable all GCC optimizations that affect signaling NaN behavior.
The default is -ffp-int-builtin-inexact, allowing the exception to be raised. This option does nothing unless -ftrapping-math is in effect.
Even if -fno-fp-int-builtin-inexact is used, if the functions generate a call to a library function then the "inexact" exception may be raised if the library implementation does not follow TS 18661.
This option controls the default setting of the ISO C99 "CX_LIMITED_RANGE" pragma. Nevertheless, the option applies to all languages.
The default is -fno-cx-fortran-rules.
The following options control optimizations that may improve performance, but are not enabled by any -O options. This section includes experimental options that may produce broken code.
With -fbranch-probabilities, GCC puts a REG_BR_PROB note on each JUMP_INSN and CALL_INSN. These can be used to improve optimization. Currently, they are only used in one place: in reorg.c, instead of guessing which path a branch is most likely to take, the REG_BR_PROB values are used to exactly determine which path is taken more often.
Enabled by -fprofile-use and -fauto-profile.
With -fbranch-probabilities, it reads back the data gathered from profiling values of expressions for usage in optimizations.
Enabled by -fprofile-generate, -fprofile-use, and -fauto-profile.
Enabled with -fprofile-use.
With -fbranch-probabilities, it reads back the data gathered and actually performs the optimizations based on them. Currently the optimizations include specialization of division operations using the knowledge about the value of the denominator.
Enabled with -fprofile-use and -fauto-profile.
Enabled by default with -funroll-loops.
Enabled at levels -O2, -O3, -Os.
Enabled by -fprofile-use and -fauto-profile.
Enabled by -fprofile-use and -fauto-profile.
Enabled by -O3, -fprofile-use, and -fauto-profile.
Enabled by -fprofile-use and -fauto-profile.
Enabled by -fprofile-use and -fauto-profile.
for (int i = 0; i < n; ++i) x[i * stride] = ...;
becomes:
if (stride == 1) for (int i = 0; i < n; ++i) x[i] = ...; else for (int i = 0; i < n; ++i) x[i * stride] = ...;
This is particularly useful for assumed-shape arrays in Fortran where (for example) it allows better vectorization assuming contiguous accesses. This flag is enabled by default at -O3. It is also enabled by -fprofile-use and -fauto-profile.
Use these options on systems where the linker can perform optimizations to improve locality of reference in the instruction space. Most systems using the ELF object format have linkers with such optimizations. On AIX, the linker rearranges sections (CSECTs) based on the call graph. The performance impact varies.
Together with a linker garbage collection (linker --gc-sections option) these options may lead to smaller statically-linked executables (after stripping).
On ELF/DWARF systems these options do not degenerate the quality of the debug information. There could be issues with other object files/debug info formats.
Only use these options when there are significant benefits from doing so. When you specify these options, the assembler and linker create larger object and executable files and are also slower. These options affect code generation. They prevent optimizations by the compiler and assembler using relative locations inside a translation unit since the locations are unknown until link time. An example of such an optimization is relaxing calls to short call instructions.
For example, the implementation of the following function "foo":
static int a, b, c; int foo (void) { return a + b + c; }
usually calculates the addresses of all three variables, but if you compile it with -fsection-anchors, it accesses the variables from a common anchor point instead. The effect is similar to the following pseudocode (which isn't valid C):
int foo (void) { register int *xr = &x; return xr[&a - &x] + xr[&b - &x] + xr[&c - &x]; }
Not all targets support this option.
The names of specific parameters, and the meaning of the values, are tied to the internals of the compiler, and are subject to change without notice in future releases.
In order to get minimal, maximal and default value of a parameter, one can use --help=param -Q options.
In each case, the value is an integer. The allowable choices for name are:
--param max-inline-insns-recursive applies to functions declared inline. For functions not declared inline, recursive inlining happens only when -finline-functions (included in -O3) is enabled; --param max-inline-insns-recursive-auto applies instead.
--param max-inline-recursive-depth applies to functions declared inline. For functions not declared inline, recursive inlining happens only when -finline-functions (included in -O3) is enabled; --param max-inline-recursive-depth-auto applies instead.
When profile feedback is available (see -fprofile-generate) the actual recursion depth can be guessed from the probability that function recurses via a given call expression. This parameter limits inlining only to call expressions whose probability exceeds the given threshold (in percents).
The tracer-dynamic-coverage-feedback parameter is used only when profile feedback is available. The real profiles (as opposed to statically estimated ones) are much less balanced allowing the threshold to be larger value.
Similarly to tracer-dynamic-coverage two parameters are provided. tracer-min-branch-probability-feedback is used for compilation with profile feedback and tracer-min-branch-probability compilation without. The value for compilation with profile feedback needs to be more conservative (higher) in order to make tracer effective.
The default is 30% + 70% * (RAM/1GB) with an upper bound of 100% when RAM >= 1GB. If "getrlimit" is available, the notion of "RAM" is the smallest of actual RAM and "RLIMIT_DATA" or "RLIMIT_AS". If GCC is not able to calculate RAM on a particular platform, the lower bound of 30% is used. Setting this parameter and ggc-min-heapsize to zero causes a full collection to occur at every opportunity. This is extremely slow, but can be useful for debugging.
The default is the smaller of RAM/8, RLIMIT_RSS, or a limit that tries to ensure that RLIMIT_DATA or RLIMIT_AS are not exceeded, but with a lower bound of 4096 (four megabytes) and an upper bound of 131072 (128 megabytes). If GCC is not able to calculate RAM on a particular platform, the lower bound is used.  Setting this parameter and ggc-min-expand to zero causes a full collection to occur at every opportunity.
Set to 1 if the prefetch hints should be issued for non-constant strides. Set to 0 if prefetch hints should be issued only for strides that are known to be constant and below prefetch-minimum-stride.
This setting is useful for processors that have hardware prefetchers, in which case there may be conflicts between the hardware prefetchers and the software prefetchers. If the hardware prefetchers have a maximum stride they can handle, it should be used here to improve the use of software prefetchers.
A value of -1 means we don't have a threshold and therefore prefetch hints can be issued for any constant stride.
This setting is only useful for strides that are known and constant.
The default choice depends on the target.
Note: By default the check is disabled at run time. To enable it, add "detect_stack_use_after_return=1" to the environment variable ASAN_OPTIONS.
You can use the function attribute "no_instrument_function" to suppress profiling of individual functions when compiling with these options.
When the compiled program exits it saves this data to a file called auxname.gcda for each source file. The data may be used for profile-directed optimizations (-fbranch-probabilities), or for test coverage analysis (-ftest-coverage). Each object file's auxname is generated from the name of the output file, if explicitly specified and it is not the final executable, otherwise it is the basename of the source file. In both cases any suffix is removed (e.g. foo.gcda for input file dir/foo.c, or dir/foo.gcda for output file specified as -o dir/foo.o).
With -fprofile-arcs, for each function of your program GCC creates a program flow graph, then finds a spanning tree for the graph. Only arcs that are not on the spanning tree have to be instrumented: the compiler adds code to count the number of times that these arcs are executed. When an arc is the only exit or only entrance to a block, the instrumentation code can be added to the block; otherwise, a new basic block must be created to hold the instrumentation code.
When an executable is run in a massive parallel environment, it is recommended to save profile to different folders. That can be done with variables in path that are exported during run-time:
The following options are enabled: -fprofile-arcs, -fprofile-values, -finline-functions, and -fipa-bit-cp.
If path is specified, GCC looks at the path to find the profile feedback data files. See -fprofile-dir.
To optimize the program based on the collected profile information, use -fprofile-use.
Warning: When an application does not properly join all threads (or creates an detached thread), a profile file can be still corrupted.
Using prefer-atomic would be transformed either to atomic, when supported by a target, or to single otherwise. The GCC driver automatically selects prefer-atomic when -pthread is present in the command line.
For example, -fprofile-filter-files=main.c;module.*.c will instrument only main.c and all C files starting with 'module'.
For example, -fprofile-exclude-files=/usr/* will prevent instrumentation of all files that are located in /usr/ folder.
Note that sanitized atomic builtins cannot throw exceptions when operating on invalid memory addresses with non-call exceptions (-fnon-call-exceptions).
signed char a = SCHAR_MAX; a++;
While -ftrapv causes traps for signed overflows to be emitted, -fsanitize=undefined gives a diagnostic message. This currently works only for the C family of languages.
Currently this feature only works for -fsanitize=undefined (and its suboptions except for -fsanitize=unreachable and -fsanitize=return), -fsanitize=float-cast-overflow, -fsanitize=float-divide-by-zero, -fsanitize=bounds-strict, -fsanitize=kernel-address and -fsanitize=address. For these sanitizers error recovery is turned on by default, except -fsanitize=address, for which this feature is experimental. -fsanitize-recover=all and -fno-sanitize-recover=all is also accepted, the former enables recovery for all sanitizers that support it, the latter disables recovery for all sanitizers that support it.
Even if a recovery mode is turned on the compiler side, it needs to be also enabled on the runtime library side, otherwise the failures are still fatal. The runtime library defaults to "halt_on_error=0" for ThreadSanitizer and UndefinedBehaviorSanitizer, while default value for AddressSanitizer is "halt_on_error=1". This can be overridden through setting the "halt_on_error" flag in the corresponding environment variable.
Syntax without an explicit opts parameter is deprecated. It is equivalent to specifying an opts list of:
undefined,float-cast-overflow,float-divide-by-zero,bounds-strict
The value "branch" tells the compiler to implement checking of validity of control-flow transfer at the point of indirect branch instructions, i.e. call/jmp instructions. The value "return" implements checking of validity at the point of returning from a function. The value "full" is an alias for specifying both "branch" and "return". The value "none" turns off instrumentation.
The macro "__CET__" is defined when -fcf-protection is used. The first bit of "__CET__" is set to 1 for the value "branch" and the second bit of "__CET__" is set to 1 for the "return".
You can also use the "nocf_check" attribute to identify which functions and calls should be skipped from instrumentation.
Currently the x86 GNU/Linux target provides an implementation based on Intel Control-flow Enforcement Technology (CET).
Note that this switch does not actually cause checking to be done; the operating system or the language runtime must do that. The switch causes generation of code to ensure that they see the stack being extended.
You can additionally specify a string parameter: no means no checking, generic means force the use of old-style checking, specific means use the best checking method and is equivalent to bare -fstack-check.
Old-style checking is a generic mechanism that requires no specific target support in the compiler but comes with the following drawbacks:
Note that old-style stack checking is also the fallback method for specific if no target support has been added in the compiler.
-fstack-check= is designed for Ada's needs to detect infinite recursion and stack overflows. specific is an excellent choice when compiling Ada code. It is not generally sufficient to protect against stack-clash attacks. To protect against those you want -fstack-clash-protection.
Most targets do not fully support stack clash protection. However, on those targets -fstack-clash-protection will protect dynamic stack allocations. -fstack-clash-protection may also provide limited protection for static stack allocations if the target supports -fstack-check=specific.
For instance, if the stack starts at absolute address 0x80000000 and grows downwards, you can use the flags -fstack-limit-symbol=__stack_limit and -Wl,--defsym,__stack_limit=0x7ffe0000 to enforce a stack limit of 128KB. Note that this may only work with the GNU linker.
You can locally override stack limit checking by using the "no_stack_limit" function attribute.
When code compiled with -fsplit-stack calls code compiled without -fsplit-stack, there may not be much stack space available for the latter code to run. If compiling all code, including library code, with -fsplit-stack is not an option, then the linker can fix up these calls so that the code compiled without -fsplit-stack always has a large stack. Support for this is implemented in the gold linker in GNU binutils release 2.21 and later.
This option causes run-time data structures to be built at program startup, which are used for verifying the vtable pointers. The options std and preinit control the timing of when these data structures are built. In both cases the data structures are built before execution reaches "main". Using -fvtable-verify=std causes the data structures to be built after shared libraries have been loaded and initialized. -fvtable-verify=preinit causes them to be built before shared libraries have been loaded and initialized.
If this option appears multiple times in the command line with different values specified, none takes highest priority over both std and preinit; preinit takes priority over std.
Note: This feature appends data to the log file. If you want a fresh log file, be sure to delete any existing one.
Note: This feature appends data to the log files. To get fresh log files, be sure to delete any existing ones.
void __cyg_profile_func_enter (void *this_fn, void *call_site); void __cyg_profile_func_exit (void *this_fn, void *call_site);
The first argument is the address of the start of the current function, which may be looked up exactly in the symbol table.