Rescanning

Once the preprocessing work has occurred, the replacement string plus the following tokens of the source file are rescanned, looking for more macro names to replace. The one exception is that, within a macro’s replacement text , the name of the macro itself is not expanded. Because macro replacement can be nested, it is possible for several macros to be in the process of being replaced at any one point: none of their names is a candidate for further replacement in the ‘inner’ levels of this process. This allows redefinition of existing functions as macros:

#define exit(x) exit((x)+1)

These macro names which were not replaced now become tokens which are immune from future replacement, even if later processing might have meant that they had become available for replacement. This prevents the danger of infinite recursion occurring in the preprocessor. The suppression of replacement is only if the macro name results directly from replacement string, not the other source text of the program. For example :

#define m(x) m((x)+1)

So
m(abc);

expands to
m((abc)+1);

even though the m ((abc)+1) above looks like a macro, the rules say it is not to be replaced

m(m(abc));

the outer m ( starts a macro invocation, but the inner one is replaced first (as above) with m((abc)+1), which becomes the argument to the outer call, giving us effectively

m(m(abc+1));

which expands to

m((m((abc+1))+1);

There is a subtle problem when using arguments to function macros.

#define SQR(X) ( X * X )

Whenever the formal parameters occurs in the replacement text , they are replaced by the actual parameters to the macro.

Printf(“sqr of %d is %d\n”, 2, SQR(2));

The formal parameter of SQR is x; the actual argument is 2. The replacement text results in

Printf(“sqr of %d is %d\n”, 2, ( 2 * 2 ));

The use of the parentheses should be noticed. The following example is likely to give trouble:

#define DOUBLE(y) y+y
Printf (“twice %d is %d\n”, 2, DOUBLE( 2 ));
Printf(“six times %d is %d/n”, 2, 3*DOUBLE ( 2 ));

The problem is that the last expression in the second printf is replaced by

3*2+2

Which results in 8, not 12. The rule is that when using macros to build expressions, careful parenthesizing is necessary. Here is another example:

SQR (3+4)

expands to
( 3+3 * 3+4 )

So, when formal parameters occur in the replacement text, you should look carefully at them too. Correct version of SQR and DOUBLE are these:

#define SQR(X) ((x)*(x))
#define DOUBLE(x) ((x)+(x))



About the Author



Silan Software is one of the India's leading provider of offline & online training for Java, Python, AI (Machine Learning, Deep Learning), Data Science, Software Development & many more emerging Technologies.

We provide Academic Training || Industrial Training || Corporate Training || Internship || Java || Python || AI using Python || Data Science etc





 PreviousNext