Are empty macro definitions allowed in C? How do they behave? Are empty macro definitions allowed in C? How do they behave? c c

Are empty macro definitions allowed in C? How do they behave?


It is simply a macro that expands to, well, nothing. However, now that the macro has been defined you can check with #if defined (or #ifdef) whether it has been defined.

#define FOOint main(){    FOO FOO FOO    printf("Hello world");}

will expand to

int main(){    printf("Hello world");}

There are certain situations where this comes in very handy, for example additional debug information, which you don't want to show in your release version:

/* Defined only during debug compilations: */#define CONFIG_USE_DEBUG_MESSAGES#ifdef CONFIG_USE_DEBUG_MESSAGES#define DEBUG_MSG(x) print(x)#else#define DEBUG_MSG(x) do {} while(0)#endifint main(){    DEBUG_MSG("Entering main");    /* ... */}

Since the macro CONFIG_USE_DEBUG_MESSAGES has been defined, DEBUG_MSG(x) will expand to print(x) and you will get Entering main. If you remove the #define, DEBUG_MSG(x) expands to an empty do-while loop and you won't see the message.


Yes, empty define is allowed by the standard.

C11 (n1570), ยง 6.10 Preprocessing directives

control-line:   # define identifier replacement-list new-line   # define identifier lparen identifier-list(opt) ) replacement-list new-line   # define identifier lparen ... ) replacement-list new-line   # define identifier lparen identifier-list , ... ) replacement-list new-linereplacement-list:    pp-tokens(opt)

A common utilisation is inclusion guards.

#ifndef F_H# define F_H#endif


Empty macro definitions can also be used for self-documentation. The IN in the code snippet below is a sample. The code and the comment are both quoted from the EDK II project.

//// Modifiers for Data Types used to self document code.// This concept is borrowed for UEFI specification.//////// Datum is passed to the function.///#define INtypedefEFI_STATUS(EFIAPI *EFI_BLOCK_RESET)(  IN EFI_BLOCK_IO_PROTOCOL          *This,  IN BOOLEAN                        ExtendedVerification  );