SS Module 4
SS Module 4
MODULE 4
MACRO PREPROCESSOR
Macro
A macro (or macro instruction)
– It is simply a notational convenience for the programmer.
– It allows the programmer to write shorthand version of a program
– It represents a commonly used group of statements in the source program.
For example:
Suppose a program needs to add two numbers frequently. This requires a sequence
of instructions. We can define and use a macro called SUM, to represent this
sequence of instructions.
Macro Preprocessor
The macro pre-processor(or macro processor) is a system software which replaces
each macro instruction with the corresponding group of source language statements.
This operation is called expanding the macro.
It does not concern the meaning of the involved statements during macro expansion.
The design of a macro processor generally is machine independent.
The fundamental functions common to all macro processors are: ( Code to remember - DIE )
o Macro Definition
o Macro Invocation
o Macro Expansion
Macro Definition
Macro definitions are typically located at the start of a program.
A macro definition is enclosed between a macro header statement(MACRO) and a
macro end statement(MEND)
Format of macro definition
macroname MACRO parameters
:
body
:
MEND
Body of macro consist of statements that will generated as the expansion of macro.
Consider the following macro definition:
SUM MACRO &X,&Y
LDA &X
MOV B
LDA &Y
ADD B
MEND
Here, the macro named SUM is used to find the sum of two variables passed to it.
Macro Expansion
Each macro invocation statement will be expanded into the statements that form the
body of the macro.
Arguments from the macro invocation are substituted for the parameters in the macro
prototype.
The arguments and parameters are associated with one another according to their
positions. The first argument in the macro invocation corresponds to the first
parameter in the macro prototype, etc.
Comment lines within the macro body have been deleted, but comments on individual
statements have been retained. Macro invocation statement itself has been included
as a comment line.
Consider the example for macro expansion on next page:
In this example, the macro named SUM is defined at the start of the program. This
macro is invoked with the macro call SUM P,Q and the macro is expanded as
LDA &P
MOV B
LDA &Q
ADD B
MEND
Again the same macro is invoked with the macro call SUM M,N and the macro is expanded
as
LDA &M
MOV B
LDA &N
ADD B
MEND
Figure: Example for macro expansion
MEND
MEND
When the macro definition for SUM is encountered, the macro name SUM along with
its parameters X and Y are entered into DEFTAB. Then the statements in the body of
macro is also entered into DEFTAB. The positional notation is used for the
parameters. The parameter &X has been converted to ?1, &Y has been converted to
?2.
The macro name SUM is entered into NAMTAB and the beginning and end pointers
are also marked.
On processing the input code, opcode in each statement is compared with the
NAMTAB, to check whether it is a macro call. When the macro call SUM P,Q is
recognized, the arguments P and Q will entered into ARGTAB. The macro is
expanded by taking the statements from DEFTAB using the beginning and end
pointers of NAMTAB.
When the ?n notation is recognized in a line from DEFTAB, the corresponding
argument is taken from ARGTAB.
Explanation of algorithm
The algorithm uses 5 procedures
o MACROPROCESSOR (main function)
o DEFINE
o EXPAND
o PROCESSLINE
o GETLINE
PROCESSLINE
This procedure checks
o If the opcode of current statement is present in NAMTAB. If so it is a macro
invocation statement and calls the procedure EXPAND
o Else if opcode =MACRO, then it indicates the beginning of a macro definition
and calls the procedure DEFINE
o Else it is identified as a normal statement(not a macro definition or macro
call) and write it to the output file.
DEFINE
The control will reach in this procedure if and only if it is identified as a macro
definition [Link]:
o Macro name is entered into NAMTAB
o Then the macro name along with its parameters are entered into DEFTAB.
o The statements in body of macro is also enterd into DEFTAB. References to
the macro instruction parameters are converted to a positional notation for
efficiency in substituting arguments.
o Comment lines from macro definition are not entered into DEFTAB because
they will not be a part of macro expansion.
o Store in NAMTAB the pointers to beginning and end of definition in
DEFTAB.
To deal with Nested macro definitions DEFINE procedure maintains a counter named
LEVEL.
o When the assembler directive MACRO is read, the value of LEVEL is
incremented by 1
o When MEND directive is read, the value of LEVEL is decremented by 1
o That is, whenever a new macro definition is encountered within the current
definition, the value of LEVEL will be incremented and the while loop which
is used to process the macro definition will terminate only after the value of
LEVEL =0. With this we can ensure the nested macro definitions are properly
handled.
EXPAND
The control will reach in this procedure if and only if it is identified as a macro call.
In this procedure, the variable EXPANDING is set to true. It actually indicates the
GETLINE procedure that it is going to expand the macro call. So that GETLINE
procedure will read the next line from DEFTAB instead of reading from input file.
The arguments of macro call are entered into ARGTAB.
The macro call is expanded with the lines from the DEFTAB. When the ?n notation is
recognized in a line from DEFTAB, the corresponding argument is taken from
ARGTAB.
GETLINE
This procedure is used to get the next line.
If EXPANDING = TRUE, the next line is fetched from DEFTAB. (It means we are
expanding the macro call)
If EXPANDING = False, the next line is read from input file.
For example, suppose that the parameter to such a macro instruction is named &ID.
The body of the macro definition contain a statement like LDA X&ID1, which means
&ID is concatenated after the string “X” and before the string “1”
TOTAL MACRO &ID
LDA X&ID1
ADD X&ID2
STA X&ID3
MEND
Ambiguity Problem: In the statement LDA X&ID1, & is the starting character of
the macro parameter; but the end of the parameter is not marked.
So X&ID1 may mean
X + &ID + 1 or X +&ID1
Most of the macro processors deal with this problem by providing a special
concatenation operator to specify the end of parameter.
Thus LDA X&ID1 can be rewritten as . So that end of the parameter
&ID is clearly defined.
Example:
The example given above shows a macro definition that uses the concatenation
operator as previously described. The statement TOTAL A and TOTAL BETA shows
the invocation statements and the corresponding macro expansion.
The macroprocessor deletes all occurrences of the concatenation operator
immediately after performing parameter substitution, so the symbol will not
appear in the macro expansion.
To avoid this we can use the technique of generating unique labels for every macro
invocation and expansion.
During macro expansion each $ will be replaced with $XX, where XX is a two
character alphanumeric counter of the number of macro instructions expansion.
For the first macro expansion in a program, XX will have the value AA. For
succeeding macro expansions XX will be set to AB,AC etc. This allows 1296 macro
expansions in a single program
Consider the following program:
SAMPLE START 0
COPY MACRO &A,&B
LDA &A
.........
$LOOP ADD &B
..........
JLE $LOOP
STA &B
MEND
.............
COPY X,Y
LDA M
COPY P,Q
...........
END
LDA M
LDA &P
.........
$ABLOOP ADD &P
.......... Expansion of COPY P,Q
JLE $ABLOOP
STA &Q
...........
END
In the example, for the first invocation of COPY X,Y the label generated is $AALOOP and
for the second invocation COPY P,Q the label generated is $ABLOOP. Thus for each
invocation of macro unique label is generated.
EVAL 2 ,3 ,4
STA Q
...............
END
After expansion the above code becomes:
COPY START 0
STA P
...................
LDA 3
ADD 4
STA Q
.........................
END
a) Positional Parameters
Parameters and arguments are associated according to their positions in the macro
prototype and invocation. The programmer must specify the arguments in proper
order.
Syntax : In macro definition,
macroname MACRO ¶meter1, ¶meter2,……
In macro invocation,
macroname argument1, argument2,….
Example: In macro definition,
EVAL MACRO &X, &Y
In macro invocation,
EVAL P,Q
Here &X recieves the value of P and &Y recieves the value of Q
If an argument is to be omitted, a null argument should be used to maintain the
proper order in macro invocation statement.
For example: Suppose a macro named EVAL has 5 possible parameters, but in a
particular invocation of the macro only the 1st and 4th parameters are to be
specified. Then the macro call will be EVAL P,,,S,
This specification overrides the default value of the parameter for the duration of that
macro call.
Consider the example:
Here the default value R is
specified for the parameter Z
INCR MACRO &X=, &Y=, &Z=R
MOV &Z, &X
ADD &Z, &Y
MOV &Z, &X
MEND
Then the macro call INCR X=A, Y=B will take the values A for parameter X, B for
parameter Y and R for the parameter Z.
The macro call INCR X=A, Y=B, Z=C will take the values A for parameter X, B for
parameter Y and C for the parameter Z.
Here the macro named INPUT is calling another macro named SUM. This is called as
recursive macro.
The macro processor design algorithm discussed previously cannot handle recursive
macro invocation and expansion.
Reasons are:
o The procedure EXPAND would be called recursively, thus the invocation
arguments in the ARGTAB will be overwritten.
o The Boolean variable EXPANDING would be set to FALSE when the “inner”
macro expansion is finished, that is, the macro process would forget that it had
been in the middle of expanding an “outer” macro.
o A similar problem would occur with PROCESSLINE since this procedure too
would be called recursively.
Solutions:
o Write the macro processor in a programming language that allows recursive calls,
thus local variables will be retained.
o If we are writing in a language without recursion support, use a stack to take care of
pushing and popping local variables and return addresses. So the recursive calls can
be handled.
The general purpose macro processor do not dependent on any particular programming
language, but can be used with a variety of different languages.
Example for a general purpose macro processor is ELENA Macro processor
Advantages
Programmers do not need to learn many macro languages, so much of the time and
expense involved in training are eliminated.
Although its development costs are somewhat greater than those for a specific language
macro processor, this expense does not need to be repeated for each language, thus save
substantial overall cost.
Disadvantages
In spite of the advantages noted, there are still relatively few general purpose macro
processors. The reasons are:
Large number of details must be dealt with in a real programming language.
There are several situations in which normal macro parameter substitution or normal
macro expansion should not occur.
o For example, comments are usually ignored by the macro processor. But each
programming languages uses its own method for specifying comments. So a
general purpose macro processor should be designed with the capability for
identifying the comments in any programming languages.
Another problem is with the facilities for grouping together terms, expressions, or
statements.
o Some languages use keywords such as begin and end for grouping statements
while some other languages uses special characters like { }. A general purpose
macro processor may need to take these groupings into account in scanning the
source statements.
Another problem is with the identification of tokens of the programming languages. The
tokens means the identifiers, constants, operators and keywords in the programming
language. Different languages uses different rules for the formation of tokens. So the
design of a general purpose macro processor must take this into consideration.
Another problem is with the syntax used for macro definitions and macro invocation
statements.
Some of the data structures required by the macro processor and the language
translator can be combined (e.g., OPTAB and NAMTAB)
Many utility subroutines can be used by both macro processor and the language
translator. This involves scanning input lines, searching tables , converting numeric
values to internal representation etc.
It is easier to give diagnostic messages related to the source statements.
TYPES OF MACRO
Different types of macro are 1. Parameterized Macro 2. Nested Macro 3. Recursive Macro
1. Parameterized Macro
Macros which uses parameters are called parameterized [Link] type of macro has
the capability to insert the given parameters into its [Link] we studied so
far belongs to this type.
Example:
SUM MACRO &X,&Y
LDA &X
MOV B
LDA &Y
ADD B
MEND
2. Nested Macros
Nested macros are macros in which definition of one macro contains definition of
other [Link] the macro definition example given below, which is used to
swap two numbers. The macro named SWAP defines another macro named STORE
inside it. These type of macro are called nested macros.
3. Recursive Macro
Invocation of one macro by another macro is called recursive [Link] for
recursive macro:
SUM MACRO &X,&Y
STA &X
ADD &Y
MEND
INPUT MACRO &A,&B
SUM &A,&B .i n v o k i n g the macro SUM
MEND
Here the macro named INPUT is calling another macro named SUM. This is called as
recursive macro.