Home > OS >  Using macro statement in macro function in C
Using macro statement in macro function in C

Time:11-11

Using #ifdef <macro> <statement> #endif allows one to have verbose messages displayed only during development and is quite handy. I wonder if something like the code below is possible, becoming even shorter:

// pseudo-code:

#define IN_DEV
#define DEBUG_ONLY(statement) (#ifdef IN_DEV (statement) #endif)

int main(void)
{
   DEBUG_ONLY(printf("hello from debug mode\n");)
   //...
}

This would only cost me a very readable one-liner which can be turned on or off. Is something like this / close to this possible?

CodePudding user response:

You could change the meaning of DEBUG_ONLY dependent on if IN_DEV is defined:

// pseudo-code:

#ifdef IN_DEV
#define DEBUG_ONLY(statement) {statement}
#else
#define DEBUG_ONLY(statement) // Nothing
#endif

int main(void)
{
   DEBUG_ONLY(printf("hello from debug mode\n");)
   //...
}

Running example: Link

CodePudding user response:

That is not possible. You cannot use #if inside a macro definition.

What you can do is this:

#define IN_DEV

#ifdef
 #define DEBUG_ONLY(statement) (statement)
#else
 #define DEBUG_ONLY(statement)
#endif

int main(void)
{
   DEBUG_ONLY(printf("hello from debug mode\n");)
   //...
}

This is also switchable with only a single macro IN_DEV.

CodePudding user response:

It doesn't make much sense to pass whole expressions as parameters to macros. That is both dangerous and unmaintainable. Worse yet, it's taking us down the obfuscation road of "lets invent our own private macro language instead of using readable C that anyone can understand". That's a terrible idea even for debugging purposes.

The more sensible approach would be a function-like printing macro which only prints something in debug build.

#ifdef INDEV
  #define DEBUG_PRINT(...) printf(__VA_ARGS__)
#else
  #define DEBUG_PRINT(...)
#endif

int main(void)
{
   DEBUG_PRINT("hello from debug mode\n");
}

Optionally this macro can be narrowed down to only accept strings and be made more type safe (C17 only):

#ifdef INDEV
  #define DEBUG_PRINT(str) _Generic((str), char*: puts(str))
#else
  #define DEBUG_PRINT(str) _Generic((str), char*: (void)0)
#endif
  • Related