Are preprocessor directives allowed in a function-like macro's argument?

This question regards the legality of using a preprocessor directive within a function-like macro’s argument.

Consider the following code. #ifdef is used inside MY_MACRO‘s argument :

#include <iostream>

// Macro to print a message along with the line number the macro appears at
#define MY_MACRO( msg ) { std::cerr << "Line " << __LINE__ << "\t- "<< msg << '\n'; }

int main()
    // Print the current build configuration
#ifdef NDEBUG // <-- preprocessor directive in macro argument

gcc 12 is fine with it, msvc 19 does not allow it :

What does the standard have to say about it?

>Solution :

Short answer: No


The sequence of preprocessing tokens bounded by the outside-most matching parentheses forms the list of arguments for the function-like macro. The individual arguments within the list are separated by comma preprocessing tokens, but comma preprocessing tokens between matching inner parentheses do not separate arguments. If there are sequences of preprocessing tokens within the list of arguments that would otherwise act as preprocessing directives, the behavior is undefined.

Leave a Reply