Jori
Jori

Reputation: 1152

How can I use # in a C preprocessor macro?

I'm trying to use a preprocessor directive in a macro? Can/how can this accomplished?

#define     HTTP_REQUEST_RETURN_ERROR(error)    *errCode = error;
                                                 #ifdef DEBUG
                                                        LeaveCriticalSection(&debugOutputLock);
                                                 #endif
                                                 return NULL

Thanks in advance, Jori.

Upvotes: 2

Views: 175

Answers (3)

unwind
unwind

Reputation: 399803

You can also, of course, define the macro twice, with different definitions:

#if defined DEBUG
#define HTTP_REQUEST_RETURN_ERROR(error) do { *errCode = error;\
                                          LeaveCriticalSection(&debugOutputLock);\
                                          return NULL;\
                                         } while(0)
#else
#define HTTP_REQUEST_RETURN_ERROR(error) do { *errCode = error;\
                                           return NULL;\
                                         } while(0)
#endif

That makes sure to avoid the (trivially optimizable) run-time if that xdazz used. It also wraps the macro bodies in the typical do ... while, to make it look like a statement.

UPDATE: To clarify, multi-statement macros in C are often wrapped (in the macro definition) in a do ... while(0) loop, since that makes the entire text into a single statement. This lets the usage of the macro work well with scopes and semicolons.

For instance, consider this:

if(httpRequestFailed())
  HTTP_REQUEST_RETURN_ERROR(404);
else
  processResults();

Without the do ... while(0), the above would be a syntax error since there would be multiple statements between the if and the else. Just adding braces to the macro expansion isn't very clean, since the desirable statement-like usage like the above would result in expansion of

if(httpRequestFailed())
  { ... /* code omitted */ };

which is not very clean, braces following a code scope are not typically followed by a semicolon.

Upvotes: 7

xdazz
xdazz

Reputation: 160833

Define DEBUG and then use the normal if statement.

#define DEBUG 0

#define HTTP_REQUEST_RETURN_ERROR(error)  *errCode = error;
                                          if (DEBUG) LeaveCriticalSection(&debugOutputLock);
                                          return NULL

Upvotes: 0

ouah
ouah

Reputation: 145829

You cannot nest preprocessor directives in a #define.

Upvotes: 4

Related Questions