Is there a way to concatenate keywords in a macro and get
C to behave in a more dynamic fashion as in:
#define macro(fun,ction,var,iable) function(variable)
I know this kind of thing exists in other languages.
You can use ## to concatinate names in macros
fun##ction ...
No. Although there is ## as Michael says, it is applied (as all preprocessing) before C or C++ looks at keywords, and even using it to generate any preprocessing keyword is allowed to crash the preprocessor.
So, as a rule, if something doesn't compile when you input it directly, it won't when generated by the preprocessor either.
There are some caveats to its use (e.g. you've got to jump through some hoops to concatenate the results of other macro expansions), but the GCC docs discuss the basic form:
http://gcc.gnu.org/onlinedocs/cpp/Concatenation.html
http://en.wikipedia.org/wiki/C_preprocessor#Token_concatenation
Related
Coming from the Ruby world, I instantly understood why Crystal chose not to implement a for method. But then I was surprised to see that Crystal does implement a for method for macros. I was even more surprised to find that macros don't allow an enumerable (.each, etc) syntax (i.e. {% ["one", "two", "three"].each do |value| %} isn't valid macro syntax).
Is there a logical reason for this syntax difference? It's possible that the answer is simply ~"because the devs decided that macro syntax looks like x, and non-macro syntax looks like y", but I'm guessing that there is more to it then that (an arbitrary syntax inconsistency seems like a flaw).
Thanks!
The main reason is that when the parser parses foo.bar do |arg| ... end, it expects an expression after |arg|, not %}, which is a parse error. So to allow that we'd need to enhance the parser (which is already quite complex) to take that into account. for was decided because of this, but also to make it clear that it's just not regular crystal but a different thing (it's an interpreted subset of crystal and the standard library).
Another reason is that if each and other iteration methods are allowed, why not while and until? That could allow endless loops in macros, which with just for aren't possible, so you can guarantee a macro finishes executing. Which... is actually not true given that we have run inside macros.
So I think I'm not opposed to change the language to allow each, each_with_index, etc., inside macros, and allow that syntax, and eventually remove for from the macro language. Opening an issue requesting this is a good way in this direction.
I know that I am trying to shoot myself in the leg ;) However, it will allow me to make the rest (big amount) of code smaller and more readable.
Is there any tricky way to create preprocessor macro inside of another preprocessor macro?
Here is the example, what I am looking for. My real scenario is more complex
// That's what I want to do and surely C++ doesn't like it.
#define MACROCREATER(B) #define MACRO##B B+B
void foo()
{
MACROCREATOR(5) // This should create new macro (#define MACRO5 5+5)
int a = MACRO5; // this will use new macro
}
The C++ Standard says (16.3.4.3):
The resulting completely
macro-replaced preprocessing token
sequence [... of the macro expansion...] is not processed as a
preprocessing directive even if it
resembles one...
So no, there is no 'official' way of achieving what you want with macros.
No. Even if a macro expands into something that looks like a preprocessing directive, the expansion is not evaluated as a preprocessing directive.
As a supplement to the answers above, if you really wanted to pre-process a source file twice—which is almost definitely not what you actually want to do—you could always invoke your compiler like this:
g++ -E input.cpp | g++ -c -x c++ - -o output.o
That is, run the file through the preprocessor, then run the preprocessed output via pipe through a full compilation routine, including a second preprocessing step. In order for this to have a reasonably good chance of working, I'd imagine you'd have to be rather careful in how you defined and used your macros, and all in all it would most likely not be worth the trouble and increased build time.
If you really want macros, use standard macro-based solutions. If you really want compile-time metaprogramming, use templates.
On a slightly related note, this reminds me of the fact that raytracing language POV-Ray made heavy use of a fairly complex preprocessing language, with flow-control directives such as #while that allowed conditional repetition, compile-time calculations, and other such goodies. Would that it were so in C++, but it simply isn't, so we just do it another way.
No. The pre-processor is single-pass. It doesn't re-evaluate the macro expansions.
As noted, one can #include a particular file more than once with different macro definitions active. This can make it practical to achieve some effects that could not be practically achieved via any other means.
As a simple example, on many embedded systems pointer indirection is very expensive compared to direct variable access. Code which uses a lot of pointer indirection may very well be twice as large and slow as code which simply uses variables. Consequently, if a particular routine is used with two sets of variables, in a scenario where one would usually pass in a pointer to a structure and then use the arrow operator, it may be far more efficient to simple put the routine in its own file (I normally use extension .i) which is #included once without macro _PASS2 defined, and a second time with. That file can then #ifdef _PASS2/#else to define macros for all the variables that should be different on the two passes. Even though the code gets generated twice, on some micros that will take less space than using the arrow operator with passed-in pointers.
Take a look at m4. It is similar to cpp, but recursive and much more powerful. I've used m4 to create a structured language for assemblers, e.g.
cmp r0, #0
if(eq)
mov r1, #0
else
add r1, #1
end
The "if", "else", and "end" are calls to m4 macros I wrote that generate jumps and labels, the rest is native assembly. In order to nest these if/else/end constructs, you need to do defines within a macro.
I'm looking for a way to extract all preprocessor symbols used in my code.
As an example, if my code looks like this:
#ifdef FOO
#endif
#if ( BAR == 1 && \
defined (Z) )
#endif
I'd like to get the list [FOO,BAR,Z] as the output.
I found some posts suggesting gcc -E -dM, but this displays all symbols that the preprocessor would apply to the code.
What I want, in contrast, is a list of all symbols actually used in the code.
Any suggestions?
That's quite simple. You have just to parse the source code exactly the way a conformant pre-processor would, and with the correct C or C++ version support. Ok, I'm joking, if you support only the later version, your code is likely to produce correct results on older versions - but even this should be thoroughly controlled.
More seriously now. As you can ask the pre-processor to give you the list of all defined symbols, you can simply tokenize the source, and identify all tokens from that list that are not immediately following an initial #define or #undef. This part should be reasonably feasable with lex+yacc.
The only alternative I can imagine would be to use the code of a real compiler (Clang should be easier than gcc but unsure) discard all code generation and consistently store every macro usage.
TL/DR: however you take it, it will be a hard work: if you can do without, keep away from that...
You can get half way there by using a preprocessor library such as Boost.Wave. It can act as a lexer so you wouldn't have to write that part yourself. You would have to supply a grammar for the bit you cared about (define, ifdef, ifndef, if, elif) though.
For example BOOST_PP_ITERATE and BOOST_PP_ITERATION, as seen on GMan's answere here, are preprocessor macros, without any parameters. Is there a reason they're not just simple defines and used as such without ()?
Generally, function like macro can be used to prevent unintentional macro
expansion.
For example, assuming that we have the following macro call:
BOOST_PP_CAT( BOOST_PP_ITERATION, _DEPTH )
and we expect this will be expanded into BOOST_PP_ITERATION_DEPTH.
However, if BOOST_PP_ITERATION is an object like(non-functional) macro,
it will be expanded to its own definition before the token
BOOST_PP_ITERATION_DEPTH is generated by concatenation.
Presumably because they perform operations: consequently, their usage should make it clear that you are actually invoking something and not just using some constant.
I know that I am trying to shoot myself in the leg ;) However, it will allow me to make the rest (big amount) of code smaller and more readable.
Is there any tricky way to create preprocessor macro inside of another preprocessor macro?
Here is the example, what I am looking for. My real scenario is more complex
// That's what I want to do and surely C++ doesn't like it.
#define MACROCREATER(B) #define MACRO##B B+B
void foo()
{
MACROCREATOR(5) // This should create new macro (#define MACRO5 5+5)
int a = MACRO5; // this will use new macro
}
The C++ Standard says (16.3.4.3):
The resulting completely
macro-replaced preprocessing token
sequence [... of the macro expansion...] is not processed as a
preprocessing directive even if it
resembles one...
So no, there is no 'official' way of achieving what you want with macros.
No. Even if a macro expands into something that looks like a preprocessing directive, the expansion is not evaluated as a preprocessing directive.
As a supplement to the answers above, if you really wanted to pre-process a source file twice—which is almost definitely not what you actually want to do—you could always invoke your compiler like this:
g++ -E input.cpp | g++ -c -x c++ - -o output.o
That is, run the file through the preprocessor, then run the preprocessed output via pipe through a full compilation routine, including a second preprocessing step. In order for this to have a reasonably good chance of working, I'd imagine you'd have to be rather careful in how you defined and used your macros, and all in all it would most likely not be worth the trouble and increased build time.
If you really want macros, use standard macro-based solutions. If you really want compile-time metaprogramming, use templates.
On a slightly related note, this reminds me of the fact that raytracing language POV-Ray made heavy use of a fairly complex preprocessing language, with flow-control directives such as #while that allowed conditional repetition, compile-time calculations, and other such goodies. Would that it were so in C++, but it simply isn't, so we just do it another way.
No. The pre-processor is single-pass. It doesn't re-evaluate the macro expansions.
As noted, one can #include a particular file more than once with different macro definitions active. This can make it practical to achieve some effects that could not be practically achieved via any other means.
As a simple example, on many embedded systems pointer indirection is very expensive compared to direct variable access. Code which uses a lot of pointer indirection may very well be twice as large and slow as code which simply uses variables. Consequently, if a particular routine is used with two sets of variables, in a scenario where one would usually pass in a pointer to a structure and then use the arrow operator, it may be far more efficient to simple put the routine in its own file (I normally use extension .i) which is #included once without macro _PASS2 defined, and a second time with. That file can then #ifdef _PASS2/#else to define macros for all the variables that should be different on the two passes. Even though the code gets generated twice, on some micros that will take less space than using the arrow operator with passed-in pointers.
Take a look at m4. It is similar to cpp, but recursive and much more powerful. I've used m4 to create a structured language for assemblers, e.g.
cmp r0, #0
if(eq)
mov r1, #0
else
add r1, #1
end
The "if", "else", and "end" are calls to m4 macros I wrote that generate jumps and labels, the rest is native assembly. In order to nest these if/else/end constructs, you need to do defines within a macro.