As a C programmer, I often find myself reasoning whether I can simplify the code I’m writing using some macros. If you are into C and GNU stuff, you can really find macros everywhere.
Typical scenario: let’s suppose you are working on an existent C program, and you find some macros you can’t figure out what they are doing. Or, worse, you are writing a macro, and you can’t understand why it is not working.
For instance, you are working on macro stringizing, and you have the following code.
#define xstr(s) str(s)
#define str(s) #s
#define foo 4
I know it’s a simple snippet, but it’s there to understand the context.
So what do you expect from the expansion of str(foo)
or from xstr(foo)
?
You can let GCC do the work for you by passing the -E
option! We can write our program again, save it as bar.c
, and test macro expansion.
#define xstr(s) str(s)
#define str(s) #s
#define foo 4
"str(foo)" -> str(foo)
"xstr(foo)" -> xstr(foo)
The nice thing here is that GCC does not perform any compilation stage or error checking with the -E
option. Hence it is easy to debug a source that is not working.
$ gcc -E bar.c
"str(foo)" -> "foo"
"xstr(foo)" -> "4"
And that’s it! The output is print over stdout
. However, you can redirect to a file if you want.
$ gcc -E bar.c > dump.c
The dump generated is a valid C
file (obv. if the C file was valid before), so you can preprocess and compile the result.