Home > Archive > Unix Programming > April 2007 > Werid <sys/queue.h> - it has useless do{} while(0)
You are viewing an archived Text-only version of the thread.
To view this thread in it's original format and/or if you want to reply to
this thread please [click here]
| Author |
Werid <sys/queue.h> - it has useless do{} while(0)
|
|
| djhong@gmail.com 2007-04-26, 7:05 pm |
| (Since queue.h is not a part of standard C, I'd lke to ask here)
For example, BSD implementation of sys/queue.h has following weird
macros:
I can't understand why "do{}while(0)" is used... Removing
"do{}while(0)" from these macros should be ok. Right?
#define SLIST_INIT(head) do { \
SLIST_FIRST((head)) = NULL; \
} while (0)
#define SLIST_INSERT_AFTER(slistelm, elm, field) do { \
SLIST_NEXT((elm), field) = SLIST_NEXT((slistelm), field); \
SLIST_NEXT((slistelm), field) = (elm); \
} while (0)
#define SLIST_INSERT_HEAD(head, elm, field) do { \
SLIST_NEXT((elm), field) = SLIST_FIRST((head)); \
SLIST_FIRST((head)) = (elm); \
} while (0)
#define SLIST_NEXT(elm, field) ((elm)->field.sle_next)
| |
| Eric Sosman 2007-04-26, 7:05 pm |
| djhong@gmail.com wrote On 04/26/07 13:47,:
> (Since queue.h is not a part of standard C, I'd lke to ask here)
>
> For example, BSD implementation of sys/queue.h has following weird
> macros:
> I can't understand why "do{}while(0)" is used... Removing
> "do{}while(0)" from these macros should be ok. Right?
>
>
> #define SLIST_INIT(head) do { \
> SLIST_FIRST((head)) = NULL; \
> } while (0)
>
> #define SLIST_INSERT_AFTER(slistelm, elm, field) do { \
> SLIST_NEXT((elm), field) = SLIST_NEXT((slistelm), field); \
> SLIST_NEXT((slistelm), field) = (elm); \
> } while (0)
>
> #define SLIST_INSERT_HEAD(head, elm, field) do { \
> SLIST_NEXT((elm), field) = SLIST_FIRST((head)); \
> SLIST_FIRST((head)) = (elm); \
> } while (0)
>
> #define SLIST_NEXT(elm, field) ((elm)->field.sle_next)
(You seem to be missing some backslashes.)
No reason I can see for do{}while(0) on the first
one, but for the next two it makes sense. Maybe the
first has do{}while(0) just for consistency's sake, or
maybe an earlier version of the first macro had more
than one statement.
The reason for the do{}while(0) dodge in multi-
statement macro expansions is to make them work right
in contexts where just one statement is allowed. For
example, try this simple macro:
#define MESSAGE(msg) { \
fputs (msg, stdout);
fputs (msg, stderr);
}
Easy enough, right? MESSAGE("Hello, world!\n") writes
the message to two output streams. But let's try it
in this context:
if (firstGreetingOfTheDay)
MESSAGE("Hello, world!\n");
else
MESSAGE("Hi again.\n");
(If you don't see the problem, feed it to a compiler
and see what it says.)
Now, you could "fix" this with documentation: "When
you use the MESSAGE macro, never put a semicolon at
the end." But that's not a really wonderful solution
because it requires the programmer to be aware that this
"function-like macro" is really a macro and not an actual
function, and requires that it be coded with a different
style than pretty much everything else. (And it will
probably raise merry Hell with automatic code formatters,
too.) The do{}while(0) dodge turns the macro expansion
into a single semicolon-terminated statement, and the
programmer's life gets simpler.
--
Eric.Sosman@sun.com
| |
| Eric Sosman 2007-04-26, 7:05 pm |
| Eric Sosman wrote On 04/26/07 14:34,:
> djhong@gmail.com wrote On 04/26/07 13:47,:
> [...]
>
> (You seem to be missing some backslashes.)
Woops! You're not missing backslashes; I was
using too narrow a window. Sorry about that.
--
Eric.Sosman@sun.com
| |
| karl malbrain 2007-04-26, 7:05 pm |
| "Eric Sosman" <Eric.Sosman@sun.com> wrote in message
news:1177612444.288279@news1nwk...
> djhong@gmail.com wrote On 04/26/07 13:47,:
>
> The reason for the do{}while(0) dodge in multi-
> statement macro expansions is to make them work right
> in contexts where just one statement is allowed.
At the expense of contexts where no statements are allowed -- only
expressions.
karl m
| |
| Eric Sosman 2007-04-26, 7:05 pm |
| karl malbrain wrote On 04/26/07 15:19,:
> "Eric Sosman" <Eric.Sosman@sun.com> wrote in message
> news:1177612444.288279@news1nwk...
>
>
>
> At the expense of contexts where no statements are allowed -- only
> expressions.
Right. But since there are no expressions that can
contain statements anyhow, much less the expansion of a
multi-statement macro, the expense is zero.
--
Eric.Sosman@sun.com
|
|
|
|
|