[gcc] GCC dump preprocessor defines

Is there a way for gcc/g++ to dump its preprocessor defines from the command line? I mean things like __GNUC__, __STDC__, and so on.

This question is related to gcc g++ c-preprocessor

The answer is


Late answer - I found the other answers useful - and wanted to add a bit extra.


How do I dump preprocessor macros coming from a particular header file?

echo "#include <sys/socket.h>" | gcc -E -dM -

or (thanks to @mymedia for the suggestion):

gcc -E -dM -include sys/socket.h - < /dev/null

In particular, I wanted to see what SOMAXCONN was defined to on my system. I know I could just open up the standard header file, but sometimes I have to search around a bit to find the header file locations. Instead I can just use this one-liner:

$ gcc -E -dM -include sys/socket.h - < /dev/null | grep SOMAXCONN
#define SOMAXCONN 128
$ 

I usually do it this way:

$ gcc -dM -E - < /dev/null

Note that some preprocessor defines are dependent on command line options - you can test these by adding the relevant options to the above command line. For example, to see which SSE3/SSE4 options are enabled by default:

$ gcc -dM -E - < /dev/null | grep SSE[34]
#define __SSE3__ 1
#define __SSSE3__ 1

and then compare this when -msse4 is specified:

$ gcc -dM -E -msse4 - < /dev/null | grep SSE[34]
#define __SSE3__ 1
#define __SSE4_1__ 1
#define __SSE4_2__ 1
#define __SSSE3__ 1

Similarly you can see which options differ between two different sets of command line options, e.g. compare preprocessor defines for optimisation levels -O0 (none) and -O3 (full):

$ gcc -dM -E -O0 - < /dev/null > /tmp/O0.txt
$ gcc -dM -E -O3 - < /dev/null > /tmp/O3.txt
$ sdiff -s /tmp/O0.txt /tmp/O3.txt 
#define __NO_INLINE__ 1        <
                               > #define __OPTIMIZE__ 1

A portable approach that works equally well on Linux or Windows (where there is no /dev/null):

echo | gcc -dM -E -

For c++ you may use (replace c++11 with whatever version you use):

echo | gcc -x c++ -std=c++11 -dM -E -

It works by telling gcc to preprocess stdin (which is produced by echo) and print all preprocessor defines (search for -dletters). If you want to know what defines are added when you include a header file you can use -dD option which is similar to -dM but does not include predefined macros:

echo "#include <stdlib.h>" | gcc -x c++ -std=c++11 -dD -E -

Note, however, that empty input still produces lots of defines with -dD option.


The simple approach (gcc -dM -E - < /dev/null) works fine for gcc but fails for g++. Recently I required a test for a C++11/C++14 feature. Recommendations for their corresponding macro names are published at https://isocpp.org/std/standing-documents/sd-6-sg10-feature-test-recommendations. But:

g++ -dM -E - < /dev/null | fgrep __cpp_alias_templates

always fails, because it silently invokes the C-drivers (as if invoked by gcc). You can see this by comparing its output against that of gcc or by adding a g++-specific command line option like (-std=c++11) which emits the error message cc1: warning: command line option ‘-std=c++11’ is valid for C++/ObjC++ but not for C.

Because (the non C++) gcc will never support "Templates Aliases" (see http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2258.pdf) you must add the -x c++ option to force the invocation of the C++ compiler (Credits for using the -x c++ options instead of an empty dummy file go to yuyichao, see below):

g++ -dM -E -x c++ /dev/null | fgrep __cpp_alias_templates

There will be no output because g++ (revision 4.9.1, defaults to -std=gnu++98) does not enable C++11-features by default. To do so, use

g++ -dM -E -x c++ -std=c++11 /dev/null | fgrep __cpp_alias_templates

which finally yields

#define __cpp_alias_templates 200704

noting that g++ 4.9.1 does support "Templates Aliases" when invoked with -std=c++11.


While working in a big project which has complex build system and where it is hard to get (or modify) the gcc/g++ command directly there is another way to see the result of macro expansion. Simply redefine the macro, and you will get output similiar to following:

file.h: note: this is the location of the previous definition
#define MACRO current_value

Examples related to gcc

Can't compile C program on a Mac after upgrade to Mojave Compiling an application for use in highly radioactive environments Make Error 127 when running trying to compile code How to Install gcc 5.3 with yum on CentOS 7.2? How does one set up the Visual Studio Code compiler/debugger to GCC? How do I set up CLion to compile and run? CMake error at CMakeLists.txt:30 (project): No CMAKE_C_COMPILER could be found How to printf a 64-bit integer as hex? Differences between arm64 and aarch64 Fatal error: iostream: No such file or directory in compiling C program using GCC

Examples related to g++

How do I set up CLion to compile and run? Compile c++14-code with g++ Fatal error: iostream: No such file or directory in compiling C program using GCC How does #include <bits/stdc++.h> work in C++? DSO missing from command line C++ unordered_map using a custom class type as the key How do I enable C++11 in gcc? usr/bin/ld: cannot find -l<nameOfTheLibrary> cc1plus: error: unrecognized command line option "-std=c++11" with g++ to_string is not a member of std, says g++ (mingw)

Examples related to c-preprocessor

Error: invalid operands of types ‘const char [35]’ and ‘const char [2]’ to binary ‘operator+’ Why does the C preprocessor interpret the word "linux" as the constant "1"? Preprocessor check if multiple defines are not defined How to use Macro argument as string literal? Define preprocessor macro through CMake? Why use #define instead of a variable How to detect reliably Mac OS X, iOS, Linux, Windows in C preprocessor? C/C++ macro string concatenation Can gcc output C code after preprocessing? How to identify platform/compiler from preprocessor macros?