Reputation: 1782
Is there a way to get the C preprocessor (GCC) to run two passes, to fully expand macros?
I'm trying to define macros that support port I/O on a microcontroller using abstract names for pins:
#define LED_RED E, (1<<6)
#define SetPin(port, mask) PORT ## port ## SET = (mask)
#define ClearPin(port, mask) PORT ## port ## CLR = (mask)
#define ReadPin(port, mask) (PORT ## port) & (mask)
Then in my code:
SetPin(LED_RED);
ClearPin(LED_RED);
result = ReadPin(LED_RED);
This is meant to expand to:
PORTESET = (1<<6);
PORTECLR = (1<<6);
result = (PORTE) & (1<<6);
This doesn't compile - I get:
error: macro "SetPin" requires 2 arguments, but only 1 given.
Although this does compile and work OK:
SetPin(E, (1<<6));
So...how to get the C compiler to fully expand these macros?
Or, if not that, how to make this kind of thing work?
Upvotes: 5
Views: 1289
Reputation: 15954
You have to pass the arguments through an additional macro.
#define LED_RED E, (1<<6)
#define SetPin2(port, mask) PORT ## port ## SET = (mask)
#define SetPin(x) SetPin2(x)
SetPin(LED_RED);
This is due to the order of macro replacement:
##
or #
, they get macro-expanded
before.With the additional macro "in between", the 2nd steps gets the chance to replace LED_RED
.
Upvotes: 13