Given the following macros giving access to compiler attributes in a function-call way, like spec(section(".mysection")) void foo(void);:
#define spec(_H_) spec_##_H_
#define spec_section(_S_) attribute ((section (_S_)))
I now would like to use these definitions in other macros, like spec(namespace(unmanaged)) int x;:
#define spec_namespace(_H_) spec_namespace_##_H_
#define spec_namespace_unmanaged spec(section(".unmanaged"))
But this does not expand at all, the only way to make it work is writting the expanded spec() macro myself:
#define spec_namespace_unmanaged spec_section(".unmanaged")
Any idea of what is going on? gcc -E on spec(namespace(unmanaged)) results inspec(namespace(unmanaged)).
Citing C99 draft 6.10.3.4 Rescanning and further replacement §2 (emphasis mine):
If the name of the macro being replaced is found during this scan of the replacement list (not including the rest of the source file’s preprocessing tokens), it is not replaced. Furthermore, if any nested replacements encounter the name of the macro being replaced, it is not replaced. These nonreplaced macro name preprocessing tokens are no longer available for further replacement even if they are later(re)examined in contexts in which that macro name preprocessing token would otherwise have been replaced.
From folowing macro-definitions:
#define spec(_H_) spec_##_H_
#define spec_namespace(_H_) spec_namespace_##_H_
#define spec_namespace_unmanaged spec(section(".unmanaged"))
It's clear that spec macro is evaluated twice, so no futher replacement is done, let's take it step-by-step:
spec(namespace(unmanaged)) int x; → spec_namespace(unmanaged) int x;
spec_namespace(unmanaged) int x; → spec_namespace_unmanaged int x;
spec_namespace_unmanaged int x; → spec(section(".unmanaged")) int x;
What you can do about it is to modify your last macro-defintion into following form:
#define spec_namespace_unmanaged attribute ((namespace (".unmanaged")))
or maybe simplify it as:
#define spec(_H_) spec_##_H_
#define spec_section(_S_) attribute ((section (_S_)))
#define spec_namespace(_N_) attribute ((namespace (_N_)))
with:
spec(namespace(".unmanaged")) int x;
To put it simply, the preprocessor will only expand a nested macro on the left side (in another macro's arguments) if neither the stringification operator # nor the concatenation operator ## are applied to it on the right side (in the macro definition).
The idiomatic way to force a nested macro expansion is to use a helper macro:
#define macro_helper(x) macro(x) // gets x expanded
Consider the following example which gets the nested __LINE__ macro expanded:
#include <iostream>
#define MACRO1(L) "Line " #L // MACRO1(__LINE__) -> "Line " "__LINE__")
#define MACRO2 MACRO1(__LINE__) // MACRO2 -> MACRO1(__LINE__)
#define MACRO3(L) "Line " #L // MACRO3(13) -> "Line " "13")
#define MACRO4(L) MACRO3(L) // MACRO4(__LINE__) -> MACRO3(13)
#define MACRO5 MACRO4(__LINE__) // MACRO5 -> MACRO4(__LINE__)
int main()
{
std::cout << MACRO2 << std::endl; // Output: "Line __LINE__"
std::cout << MACRO5 << std::endl; // Output: "Line 13"
}
Related
I'm trying to concatenate a macro call with a token to create a new one, for instance:
#define TEST(X) X ## _TEST
#define CONCAT(X) TEST(X) ## _CONCAT
CONCAT(OK);
Then I check the output with gcc -E; I would want to get OK_TEST_CONCAT; but instead I get an error:
error: pasting ")" and "_CONCAT" does not give a valid preprocessing token
If I remove ## I get no error but the output is OK_TEST _CONCAT;
This is a minimal example, so the easiest here would be to combine everything in a single macro, but know that it's impossible for me to get rid of the first call to TEST. Is there a way to remove that space?
Thanks
EDIT:
Ok so from the confusion maybe my example was a little too minimal, that's my fault. Here is a more plausible use case:
I want all the prototypes in a certain header to be prefixed by the PREFIX defined in that header.
proto.h:
#define EXPAND(X) EXPAND_HELPER(X)
#define EXPAND_HELPER(X) X
#define PROTO(NAME) PREFIX ## NAME
other.h:
#include <proto.h>
#define PREFIX other
int PROTO(test)(int a, int b);
...
What I want is all the prototypes in other.h to have this form: int other_test(int a, int b);. But as it is they have this form: int PREFIX_test(int a, int b);. After googling I found that I needed to force PREFIX to rescan, so I tried this:
#define PROTO(NAME) EXPAND(PREFIX) ## NAME
which prompted my question. Now if I look at #Lundin's answer, I can adapt it to give what I want:
Solution:
#define PROTO(NAME) PROTO_HELPER(PREFIX, NAME)
#define PROTO_HELPER(PREFIX, NAME) PROTO_EXPAND(PREFIX, NAME)
#define PROTO_EXPAND(PREFIX, NAME) PREFIX ## NAME
Thanks!
All preprocessor tokens must be expanded before a function-like macro using ## or # is called. Because ## or # is applied before macro expansion. In your case TEST(X) only expands X into TEST(OK) and then the preprocessor attempts to paste TEST(OK) with _CONCAT which won't work. For each attempt to concatenate tokens, you must first expand all macros before ##, which is done by extra helper macros that force a rescanning/replacement.
The contrived solution given #define TEST(X) X ## _TEST would be this:
#define CONCAT(X) EXPAND_HELPER(TEST(X)) // expands TEST(X) to TEST(OK)
-->
#define EXPAND_HELPER(X) CONCAT_HELPER(X, _CONCAT) // expands TEST(OK) to OK_TEST
-->
#define CONCAT_HELPER(X,Y) X ## Y
That is:
// NOTE: contrived solution, avoid
#define TEST(X) X ## _TEST
#define CONCAT_HELPER(X,Y) X ## Y
#define EXPAND_HELPER(X) CONCAT_HELPER(X, _CONCAT)
#define CONCAT(X) EXPAND_HELPER(TEST(X))
...
int CONCAT(OK) = 1; // becomes int OK_TEST_CONCAT = 1;
A much simpler solution would be:
#define CONCAT(X) X ## _TEST ## _CONCAT
Background
In a separate question of mine, I created a function-like-macro that allows me to concatenate a user-supplied text literal to create a macro name, i.e.:
/******************************************************************************
* coconut.h
******************************************************************************/
#define COCONUT_FX_REGISTER (100)
#define COCONUT_BASE_REGISTER (101)
/*******************************************************************************
* pineapple.h
******************************************************************************/
#define PINEAPPLE_FX_REGISTER (200)
#define PINEAPPLE_BASE_REGISTER (201)
/*******************************************************************************
* test.c.
******************************************************************************/
#include <stdio.h>
#include "translation.h"
#include "coconut.h"
#include "pineapple.h"
int main(void) {
int i = getTranslation(FX_REGISTER, COCONUT);
printf("Translation:%d.\n", i);
return 0;
}
/*******************************************************************************
* translation.h
******************************************************************************/
#define getTranslation(x, y) y ## _ ## x
Goal
I would like to extend this logic so that I can use a macro for a default value to pass to getTranslation, i.e.:
#define XFRM(x) #x
#define XFRM2(x) XFRM(x)
#define DEFAULT_PRODUCT XFRM2(COCONUT)
int main(void) {
int i = getTranslation(FX_REGISTER, DEFAULT_PRODUCT);
printf("Translation:%d.\n", i);
return 0;
}
Problem
However, I can't seem to get DEFAULT_PRODUCT to be converted to a non-string text literal.
Build Errors
main.c: In function ‘main’:
main.c:14:35: error: ‘DEFAULT_PRODUCT_FX_REGISTER’ undeclared (first use in this function)
printf("%d\n", getTranslation(FX_REGISTER, DEFAULT_PRODUCT));
^
translation.h:33:25: note: in definition of macro ‘getTranslation’
#define getTranslation(x, y) y ## _ ## x
^
main.c:14:35: note: each undeclared identifier is reported only once for each function it appears in
printf("%d\n", getTranslation(FX_REGISTER, DEFAULT_PRODUCT));
^
translation.h:33:25: note: in definition of macro ‘getTranslation’
#define getTranslation(x, y) y ## _ ## x
Question
How can I create a DEFAULT_PRODUCT macro that resolves to a non-string text literal so that I can create a "default" value to use with getTranslation? This is using GCC set to C99 pedantic.
Sounds like an XY problem.
It seems that macro concatenations are processed simultaneous to macro literal expansions, so I'm afraid there's no way to create a DEFAULT_PRODUCT macro that gets expanded before getTranslation.
My proposal: Create another macro function getDefaultTranslation(x) and you'll easily achieve what you want.
// You may want to add appropriate comments
// so code reviewers know what this is doing.
#define getDefaultTranslation(x) COCONUT ## x
Regarding this question, macro expansion is done layer-by-layer, and at the same layer concatenation has a higher precedence , so adding another layer should work. See ringø's answer below.
You need to add an indirection in order to let the preprocessor expand the macros before doing the concatenation
#define CONCAT(a, b) a ## _ ## b
#define getTranslation(x, y) CONCAT(x,y)
#define XFRM(x) x
#define XFRM2(x) XFRM(x)
#define DEFAULT_PRODUCT XFRM2(COCONUT)
Note that XFRM has its # removed (off x), otherwise the " gives an invalid preprocessing token.
This way you get
int i = FX_REGISTER_COCONUT;
I have concrete_impl.h (as is):
#ifdef TUPLE_ITERATOR_WITH_INDEX
#define TUPLE_ITERATOR TUPLE_ITERATOR_NO_INDEX
#define iterate_tuple_fname iterate_tuple_id
#else
#define TUPLE_ITERATOR TUPLE_ITERATOR_INDEX
#define iterate_tuple_fname iterate_tuple
#endif
#undef iterate_tuple_fname_back
#define iterate_tuple_fname_back iterate_tuple_fname##_back
static void iterate_tuple_fname() // ok
{
}
static void iterate_tuple_fname_back() // redefinition error
{
}
And concrete.h (as is):
#ifndef CONCRETE_H
#define CONCRETE_H
#define TUPLE_ITERATOR_WITH_INDEX
#include "concrete_impl.h"
#undef TUPLE_ITERATOR_WITH_INDEX
#include "concrete_impl.h"
#endif // CONCRETE_H
What I want to get - is 4 functions:
iterate_tuple
iterate_tuple_id
iterate_tuple_back
iterate_tuple_id_back
But on "_back" functions I have redefinition error. Why?
iterate_tuple_fname##_back is nothing else than iterate_tuple_fname_back. To have iterate_tuple_fname replaced by its macro replacement list, you'll need a helper macro:
#define CONCAT(a, b) a ## b
#define iterate_tuple_fname_back CONCAT(iterate_tuple_fname, _back)
UPDATE: Sorry, have forgotten all about C after several years of C# programming.
It actually needs double run through helper macros:
#define CONCAT1(a, b) a ## b
#define CONCAT(a, b) CONCAT1(a, b)
#define iterate_tuple_fname_back CONCAT(iterate_tuple_fname, _back)
Apparently you misunderstand how the ## operator works.
If the preprocessing token adjacent to the ## operator is a parameter of the current macro, then this parameter is recursively analyzed for further replacement first, and the result of that replacement substituted into the result.
If the preprocessing token adjacent to the ## operator is not a parameter of the current macro, then recursive analysis and replacement of that token does not take place. The token is simply concatenated with the other token.
Later, once all parameters are substituted and all concatenations are joined, the entire result is rescanned again for further replacements. But then it is already be too late for your example.
In your case you defined this macro
#define iterate_tuple_fname_back iterate_tuple_fname##_back
Since iterate_tuple_fname is not a parameter of this macro, no early replacement occurs for iterate_tuple_fname. The whole thing is immediately concatenated into iterate_tuple_fname_back and only after that it is rescanned. But rescan finds nothing to replace there, so iterate_tuple_fname_back is the final result.
If you want the preprocessor to replace the left-hand side of the ## operator (which was your intent apparently), you absolutely have to use a macro parameter on the left-hand side, as in
#define ITF_back(prefix) prefix##_back
and then you can use this macro as
ITF_back(iterate_tuple_fname)
Now the rescan and recursive replacement inside iterate_tuple_fname will occur early, before the concatenation with the _back part. I.e. it will work as you wanted it to.
I am having trouble getting this macro expanison right
#define foo Hello
#ifdef foo
#define wrapper(x) foo ## x
#else
#define wrapper(x) boo ## x
#endif
calling:
wrapper(_world)
I would like the result of
Hello_world
however, the macro is treating the "foo" define as a literal, and thus giving
foo_world
Can someone point out my mistake?
Thanks
I would recommend gnu-cpp-manual which clearly explains how macros are expanded.
Macro arguments are completely macro-expanded before they are substituted into a macro body, unless they(macro arguments) are stringified or pasted with other tokens (by the macro function that is directly applied to).
For example:
If an argument is stringified or concatenated, the prescan does not occur.
#define AFTERX(x) X_ ## x
#define XAFTERX(x) AFTERX(x)
#define TABLESIZE 1024
#define BUFSIZE TABLESIZE
AFTERX(BUFSIZE) => X_BUFSIZE: since AFTERX is to concatenate argument with prefix, its argument is not expanded, remaining BUFSIZE.
XAFTERX(BUFSIZE) => X_1024: XAFTERX does not do concatenation directly, so BUFSIZE will be expanded first.
Generally, arguments are scanned twice to expand macro called in them.
--- edit ---
So the better practice is: (code from QEMU source)
#ifndef glue
#define xglue(x, y) x ## y
#define glue(x, y) xglue(x, y)
#define stringify(s) tostring(s)
#define tostring(s) #s
#endif
glue(x,y) will concatenate x and y with both already expanded.
I want to define a macro function which support at the same time:
1) No input parameter
2) Input parameters
some thing like that:
#define MACRO_TEST(X)\
printf("this is a test\n");\
printf("%d\n",x) // the last printf should not executed if there is no input parameter when calling the macro
In the main:
int main()
{
MACRO_TEST(); // This should display only the first printf in the macro
MACRO_TEST(5); // This should display both printf in the macro
}
You can use sizeof for this purpose.
Consider something like this:
#define MACRO_TEST(X) { \
int args[] = {X}; \
printf("this is a test\n");\
if(sizeof(args) > 0) \
printf("%d\n",*args); \
}
gcc and recent versions of MS compilers support variadic macros - that is macros that work similar to printf.
gcc documentation here:
http://gcc.gnu.org/onlinedocs/gcc/Variadic-Macros.html
Microsoft documentation here:
http://msdn.microsoft.com/en-us/library/ms177415(v=vs.80).aspx
Not exactly that but ...
#include <stdio.h>
#define MTEST_
#define MTEST__(x) printf("%d\n",x)
#define MACRO_TEST(x)\
printf("this is a test\n");\
MTEST_##x
int main(void)
{
MACRO_TEST();
MACRO_TEST(_(5));
return 0;
}
EDIT
And if 0 can be used as skip:
#include <stdio.h>
#define MACRO_TEST(x) \
do { \
printf("this is a test\n"); \
if (x +0) printf("%d\n", x +0); \
} while(0)
int main(void)
{
MACRO_TEST();
MACRO_TEST(5);
return 0;
}
The C99 standard says,
An identifier currently defined as an object-like macro shall not be redefined by another #define reprocessing directive unless the second definition is an object-like macro definition and the two replacement lists are identical. Likewise, an identifier currently defined as a function-like macro shall not be redefined by another #define preprocessing directive unless the second definition is a function-like macro definition that has the same number and spelling of parameters, and the two replacement lists are identical.
I think compiler prompts a warning of redefined MACRO. Hence it is not possible.