5.8.4 Macro Directive
The .macro name [args]
and .endm directives allow you to define macros that
generate assembly output.
The macro will be called name. If required, it can take
arguments when it is used. To allow this, follow the macro name with a list of the argument
names with either a space character or comma separating them. A default value can be
specified with any argument by following its name with
=value.
The following are valid opening lines for macro definitions.
.macro comm– Begin the definition of a macro calledcomm, which takes no arguments..macro plus1 p, p1or.macro plus1 p p1– Either statement begins the definition of a macro calledplus1, which takes two arguments; within the macro definition, write\por\p1to evaluate the arguments..macro reserve_str p1=0 p2– Begin the definition of a macro calledreserve_str, with two arguments. The first argument has a default value, but not the second. After the definition is complete, you can call the macro either asreserve_str a,b(with\p1evaluating toaand\p2evaluating tob), or asreserve_str ,b(with\p1evaluating as the default, in this case0, and\p2evaluating tob).
For example, this definition specifies a macro
SUM with
two arguments, from and to, that puts a sequence of
numbers into memory:.macro SUM from=0, to=3
.long \from
.if \+o-\from
SUM "(\from+1)", \+o
.endif
.endmThe above macro could be used (called), specifying the arguments values,
for example,
SUM 0,5, which would expand to the
following:.long 0
.long 1
.long 2
.long 3
.long 4
.long 5When you call a macro, you can specify the argument values either by
position, or by keyword. For example, SUM 9,17 is
equivalent to SUM to=17, from=9.
The assembler maintains a counter of how many macros it has executed. You
can copy that number to the output by using the
\@
operator, but only within a macro definition. In the following example, a recursive macro
is used to allocate an arbitrary number of labeled
buffers. .macro make_buffers num,size
BUF\@: .space \size
.if (\num - 1)
make_buffers (\num - 1),\size
.endif
.endm
.bss
# create BUF0..BUF3, 16 bytes each
make_buffers 4,16This example macro expands as shown in the following
listing.
6 make_buffers (\num - 1),\size
7 .endif
8 .endm
9
10 .bss
11 # create BUF0..BUF3, 16 bytes each
12 make_buffers 4,16
12 > BUF0:.space 16
12 0000 > .space 16
12 > .if (4-1)
12 > make_buffers (4-1),16
12 >> BUF1:.space 16
12 0010 >> .space 16
12 >> .if ((4-1)-1)
12 >> make_buffers ((4-1)-1),16
12 >>> BUF2:.space 16
12 0020 >>> .space 16
12 >>> .if (((4-1)-1)-1)
12 >>> make_buffers (((4-1)-1)-1),16
12 >>>> BUF3:.space 16
12 0030 >>>> .space 16
12 >>>> .if ((((4-1)-1)-1)-1)
12 >>>> make_buffers ((((4-1)-1)-1)-1),16
12 >>>> .endif
12 >>> .endif
12 >> .endif
12 > .endif