What's the use of do while(0) when we define a macro?

You can follow it with a semicolon and make it look and act more like a function. It also works with if/else clauses properly then.

Without the while(0), your code above would not work with

if (doit) 
   INIT_LIST_HEAD(x);
 else 
   displayError(x);

since the semicolon after the macro would "eat" the else clause, and the above wouldn't even compile.


It allows you to group several statements into one macro.

Assume you did something like:

if (foo) 
    INIT_LIST_HEAD(bar);

If the macro was defined without the encapsulating do { ... } while (0);, the above code would expand to

if (foo)
    (bar)->next = (bar);
    (bar)->prev = (bar);

This is clearly not what was intended, as only the first statement will be executed if foo holds. The second statement would be executed regardless of whether foo holds.

Edit: Further explanation at http://c-faq.com/cpp/multistmt.html and http://developer.apple.com/documentation/DeveloperTools/gcc-4.0.1/cpp/Swallowing-the-Semicolon.html#Swallowing-the-Semicolon