ARM Assembly
Language Tools
v18.1.0.LTS User's Guide
SPNU118U - REVISED JANUARY 2018
6 Macro Language Description
The ARM device assembler supports a macro language that enables you to create your own instructions. This is especially useful when a program executes a particular task several times. The macro language lets you:
- Define your own macros and redefine existing macros
- Simplify long or complicated assembly code
- Access macro libraries created with the archiver
- Define conditional and repeatable blocks within a macro
- Manipulate strings within a macro
- Control expansion listing
6.1 Using Macros
Programs often contain routines that are executed several times. Instead of repeating the source statements for a routine, you can define the routine as a macro, then call the macro in the places where you would normally repeat the routine. This simplifies and shortens your source program.
If you want to call a macro several times but with different data each time, you can assign parameters within a macro. This enables you to pass different information to the macro each time you call it. The macro language supports a special symbol called a substitution symbol, which is used for macro parameters. See Section 6.3 for more information.
Using a macro is a 3-step process.
-
Define the macro. You must define macros before you can use them in your program. There are two methods for defining macros:
- Macros can be defined at the beginning of a source file or in a copy/include file. See Section 6.2, Defining Macros, for more information.
- Macros can also be defined in a macro library. A macro library is a collection of files in archive format created by the archiver. Each member of the archive file (macro library) may contain one macro definition corresponding to the member name. You can access a macro library by using the .mlib directive. For more information, see Section 6.4.
- Call the macro. After you have defined a macro, call it by using the macro name as a mnemonic in the source program. This is referred to as a macro call.
- Expand the macro. The assembler expands your macros when the source program calls them. During expansion, the assembler passes arguments by variable to the macro parameters, replaces the macro call statement with the macro definition, then assembles the source code. By default, the macro expansions are printed in the listing file. You can turn off expansion listing by using the .mnolist directive. For more information, see Section 6.8.
When the assembler encounters a macro definition, it places the macro name in the opcode table. This redefines any previously defined macro, library entry, directive, or instruction mnemonic that has the same name as the macro. This allows you to expand the functions of directives and instructions, as well as to add new instructions.
6.2 Defining Macros
You can define a macro anywhere in your program, but you must define the macro before you can use it. Macros can be defined at the beginning of a source file or in a .copy/.include file (see Copy Source File); they can also be defined in a macro library. For more information about macro libraries, see Section 6.4.
Macro definitions can be nested, and they can call other macros, but all elements of the macro must be defined in the same file. Nested macros are discussed in Section 6.9.
A macro definition is a series of source statements in the following format:
macname | .macro [parameter1 ] [, ... ,parametern ] |
model statements or macro directives | |
[.mexit] | |
.endm |
macname | names the macro. You must place the name in the source statement's label field. Only the first 128 characters of a macro name are significant. The assembler places the macro name in the internal opcode table, replacing any instruction or previous macro definition with the same name. |
.macro | is the directive that identifies the source statement as the first line of a macro definition. You must place .macro in the opcode field. |
parameter1, parametern |
are optional substitution symbols that appear as operands for the .macro directive. Parameters are discussed in Section 6.3. |
model statements | are instructions or assembler directives that are executed each time the macro is called. |
macro directives | are used to control macro expansion. |
.mexit | is a directive that functions as a goto .endm. The .mexit directive is useful when error testing confirms that macro expansion fails and completing the rest of the macro is unnecessary. |
.endm | is the directive that terminates the macro definition. |
If you want to include comments with your macro definition but do not want those comments to appear in the macro expansion, use an exclamation point to precede your comments. If you do want your comments to appear in the macro expansion, use an asterisk or semicolon. See Section 6.7 for more information about macro comments.
Example 6-1 shows the definition, call, and expansion of a macro.
Example 6-1 Macro Definition, Call, and Expansion
Macro definition: The following code defines a macro, add3, with four parameters:
1 *
2
3 * add3
4 *
5 * ADDRP = P1 + P2 + P3
6
7 add3 .macro P1, P2, P3, ADDRP
8
9 ADD ADDRP, P1, P2
10 ADD ADDRP, ADDRP, P3
11 .endm
Macro call: The following code calls the add3 macro with four arguments:
12
13 00000000 add3 R1, R2, R3, R0
Macro expansion: The following code shows the substitution of the macro definition for the macro call. The assembler substitutes R1, R2, R3, and R0 for the P1, P2, P3, and ADDRP parameters of add3.
1
1 00000000 E0810002 ADD R0, R1, R2
1 00000004 E0800003 ADD R0, R0, R3
6.3 Macro Parameters/Substitution Symbols
If you want to call a macro several times with different data each time, you can assign parameters within the macro. The macro language supports a special symbol, called a substitution symbol, which is used for macro parameters.
Macro parameters are substitution symbols that represent a character string. These symbols can also be used outside of macros to equate a character string to a symbol name (see Section 4.8.8).
Valid substitution symbols can be up to 128 characters long and must begin with a letter. The remainder of the symbol can be a combination of alphanumeric characters, underscores, and dollar signs.
Substitution symbols used as macro parameters are local to the macro they are defined in. You can define up to 32 local substitution symbols (including substitution symbols defined with the .var directive) per macro. For more information about the .var directive, see Section 6.3.6.
During macro expansion, the assembler passes arguments by variable to the macro parameters. The character-string equivalent of each argument is assigned to the corresponding parameter. Parameters without corresponding arguments are set to the null string. If the number of arguments exceeds the number of parameters, the last parameter is assigned the character-string equivalent of all remaining arguments.
If you pass a list of arguments to one parameter or if you pass a comma or semicolon to a parameter, you must surround these terms with quotation marks.
At assembly time, the assembler replaces the macro parameter/substitution symbol with its corresponding character string, then translates the source code into object code.
Example 6-2 shows the expansion of a macro with varying numbers of arguments.
Example 6-2 Calling a Macro With Varying Numbers of Arguments
Macro definition:
Parms .macro a,b,c
; a = :a:
; b = :b:
; c = :c:
.endm
Calling the macro:
Parms 100,label Parms 100,label,x,y
; a = 100 ; a = 100
; b = label ; b = label
; c = "" ; c = x,y
Parms 100, , x Parms "100,200,300",x,y
; a = 100 ; a = 100,200,300
; b = "" ; b = x
; c = x ; c = y
Parms """string""",x,y
; a = "string"; b = x
; c = y
6.3.1 Directives That Define Substitution Symbols
You can manipulate substitution symbols with the .asg and .eval directives.
- The .asg directive assigns a character string to a substitution symbol.
For the .asg directive, the quotation marks are optional. If there are no quotation marks, the assembler reads characters up to the first comma and removes leading and trailing blanks. In either case, a character string is read and assigned to the substitution symbol. The syntax of the .asg directive is:
.asg["]character string["], substitution symbol |
Example 6-3 shows character strings being assigned to substitution symbols.
- The .eval directive performs arithmetic on numeric substitution symbols.
The .eval directive evaluates the expression and assigns the string value of the result to the substitution symbol. If the expression is not well defined, the assembler generates an error and assigns the null string to the symbol. The syntax of the .eval directive is:
.evalwell-defined expression, substitution symbol |
Example 6-4 shows arithmetic being performed on substitution symbols.
Example 6-4 The .eval Directive
.asg 1,counter
.loop 100
.word counter
.eval counter + 1,counter
.endloop
In Example 6-4, the .asg directive could be replaced with the .eval directive (.eval 1, counter) without changing the output. In simple cases like this, you can use .eval and .asg interchangeably. However, you must use .eval if you want to calculate a value from an expression. While .asg only assigns a character string to a substitution symbol, .eval evaluates an expression and then assigns the character string equivalent to a substitution symbol.
See Assign a Substitution Symbol for more information about the .asg and .eval assembler directives.
6.3.2 Built-In Substitution Symbol Functions
The following built-in substitution symbol functions enable you to make decisions on the basis of the string value of substitution symbols. These functions always return a value, and they can be used in expressions. Built-in substitution symbol functions are especially useful in conditional assembly expressions. Parameters of these functions are substitution symbols or character-string constants.
In the function definitions shown in Table 6-1, a and b are parameters that represent substitution symbols or character-string constants. The term string refers to the string value of the parameter. The symbol ch represents a character constant.
Table 6-1 Substitution Symbol Functions and Return Values
Function | Return Value |
---|---|
$$symlen(a) | Length of string a |
$$symcmp(a,b) | < 0 if a < b; 0 if a = b; > 0 if a > b |
$$firstch(a,ch) | Index of the first occurrence of character constant ch in string a |
$$lastch(a,ch) | Index of the last occurrence of character constant ch in string a |
$$isdefed(a) | 1 if string a is defined in the symbol table |
0 if string a is not defined in the symbol table | |
$$ismember(a,b) | Top member of list b is assigned to string a |
0 if b is a null string | |
$$iscons(a) | 1 if string a is a binary constant |
2 if string a is an octal constant | |
3 if string a is a hexadecimal constant | |
4 if string a is a character constant | |
5 if string a is a decimal constant | |
$$isname(a) | 1 if string a is a valid symbol name |
0 if string a is not a valid symbol name | |
$$isreg(a)(1) | 1 if string a is a valid predefined register name |
0 if string a is not a valid predefined register name |
Example 6-5 shows built-in substitution symbol functions.
Example 6-5 Using Built-In Substitution Symbol Functions
.asg label, ADDR ; ADDR = label
.if ($$symcmp(ADDR, "label") = 0) ; evaluates to true
LDR R4, ADDR
.endif
.asg "x,y,z" , list ; list = x,y,z
.if ($$ismember(ADDR,list)) ; ADDR = x, list = y,z
SUB R4, R4, #4 ; sub x
.endif
6.3.3 Recursive Substitution Symbols
When the assembler encounters a substitution symbol, it attempts to substitute the corresponding character string. If that string is also a substitution symbol, the assembler performs substitution again. The assembler continues doing this until it encounters a token that is not a substitution symbol or until it encounters a substitution symbol that it has already encountered during this evaluation.
In Example 6-6, the x is substituted for z; z is substituted for y; and y is substituted for x. The assembler recognizes this as infinite recursion and ceases substitution.
Example 6-6 Recursive Substitution
.asg "x",z ; declare z and assign z = "x" .asg "z",y ; declare y and assign y = "z" .asg "y",x ; declare x and assign x = "y" LDR R0, x
* LDR R0, x ; recursive expansion
6.3.4 Forced Substitution
In some cases, substitution symbols are not recognizable to the assembler. The forced substitution operator, which is a set of colons surrounding the symbol, enables you to force the substitution of a symbol's character string. Simply enclose a symbol with colons to force the substitution. Do not include any spaces between the colons and the symbol. The syntax for the forced substitution operator is:
:symbol: |
The assembler expands substitution symbols surrounded by colons before expanding other substitution symbols.
You can use the forced substitution operator only inside macros, and you cannot nest a forced substitution operator within another forced substitution operator.
Example 6-7 shows how the forced substitution operator is used.
Example 6-7 Using the Forced Substitution Operator
1 force .macro
2 .asg 0,x
3 .loop 8
4 AUX:x: .set x
5 .eval x+1,x
6 .endloop
7 .endm
8
9 00000000 force
1 .asg 0,x
1 .loop 8
1 AUX:x: .set x
1 .eval x+1,x
1 .endloop
2 00000000 AUX0 .set 0
2 .eval 0+1,x
2 00000001 AUX1 .set 1
2 .eval 1+1,x
2 00000002 AUX2 .set 2
2 .eval 2+1,x
2 00000003 AUX3 .set 3
2 .eval 3+1,x
2 00000004 AUX4 .set 4
2 .eval 4+1,x
2 00000005 AUX5 .set 5
2 .eval 5+1,x
2 00000006 AUX6 .set 6
2 .eval 6+1,x
2 00000007 AUX7 .set 7
2 .eval 7+1,x
6.3.5 Accessing Individual Characters of Subscripted Substitution Symbols
In a macro, you can access the individual characters (substrings) of a substitution symbol with subscripted substitution symbols. You must use the forced substitution operator for clarity.
You can access substrings in two ways:
- :symbol (well-defined expression):
- :symbol (well-defined expression1, well-defined expression2):
This method of subscripting evaluates to a character string with one character.
In this method, expression1 represents the substring's starting position, and expression2 represents the substring's length. You can specify exactly where to begin subscripting and the exact length of the resulting character string. The index of substring characters begins with 1, not 0.
Example 6-8 and Example 6-9 show built-in substitution symbol functions used with subscripted substitution symbols. In Example 6-8, subscripted substitution symbols redefine the ADD instruction so that it handles short immediate values. In Example 6-9, the subscripted substitution symbol is used to find a substring strg1 beginning at position start in the string strg2. The position of the substring strg1 is assigned to the substitution symbol pos.
Example 6-8 Using Subscripted Substitution Symbols to Redefine an Instruction
ADDX .macro dst, imm
.var TMP
.asg :imm(1):, TMP
.if $$symcmp(TMP,"#") = 0
ADD dst, dst, imm
.else
.emsg "Bad Macro Parameter" .endif
.endm
ADDX R9, #100 ; macro call
ADDX R9, R8 ; macro call
Example 6-9 Using Subscripted Substitution Symbols to Find Substrings
substr .macro start,strg1,strg2,pos
.var LEN1,LEN2,I,TMP
.if $$symlen(start) = 0
.eval 1,start
.endif
.eval 0,pos
.eval 1,i
.eval $$symlen(strg1),LEN1
.eval $$symlen(strg2),LEN2
.loop
.break I = (LEN2 - LEN1 + 1)
.asg ":strg2(I,LEN1):",TMP
.eval i,pos
.break
.else
.eval I + 1,i
.endif
.endloop
.endm
.asg 0,pos
.asg "ar1 ar2 ar3 ar4",regs
substr 1,"ar2",regs,pos
.word pos
6.3.6 Substitution Symbols as Local Variables in Macros
If you want to use substitution symbols as local variables within a macro, you can use the .var directive to define up to 32 local macro substitution symbols (including parameters) per macro. The .var directive creates temporary substitution symbols with the initial value of the null string. These symbols are not passed in as parameters, and they are lost after expansion.
.var sym1 [,sym2 , ... ,symn ] |
The .var directive is used in Example 6-8 and Example 6-9.
6.4 Macro Libraries
One way to define macros is by creating a macro library. A macro library is a collection of files that contain macro definitions. You must use the archiver to collect these files, or members, into a single file (called an archive). Each member of a macro library contains one macro definition. The files in a macro library must be unassembled source files. The macro name and the member name must be the same, and the macro filename's extension must be .asm. For example:
Macro Name | Filename in Macro Library |
---|---|
simple | simple.asm |
add3 | add3.asm |
You can access the macro library by using the .mlib assembler directive (described in Define Macro Library). The syntax is:
.mlibfilename |
When the assembler encounters the .mlib directive, it opens the library named by filename and creates a table of the library's contents. The assembler enters the names of the individual members within the library into the opcode tables as library entries; this redefines any existing opcodes or macros that have the same name. If one of these macros is called, the assembler extracts the entry from the library and loads it into the macro table.
The assembler expands the library entry the same way it expands other macros. See Section 6.1 for how the assembler expands macros. You can control the listing of library entry expansions with the .mlist directive. For information about the .mlist directive, see Section 6.8 and Start/Stop Macro Expansion Listing. Only macros that are actually called from the library are extracted, and they are extracted only once.
You can use the archiver to create a macro library by including the desired files in an archive. A macro library is no different from any other archive, except that the assembler expects the macro library to contain macro definitions. The assembler expects only macro definitions in a macro library; putting object code or miscellaneous source files into the library may produce undesirable results. For information about creating a macro library archive, see Section 7.1.
6.5 Using Conditional Assembly in Macros
The conditional assembly directives are .if/.elseif/.else/.endif and .loop/ .break/.endloop. They can be nested within each other up to 32 levels deep. The format of a conditional block is:
.ifwell-defined expression | |
[.elseifwell-defined expression] | |
[.else] | |
.endif |
The .elseif and .else directives are optional in conditional assembly. The .elseif directive can be used more than once within a conditional assembly code block. When .elseif and .else are omitted and when the .if expression is false (0), the assembler continues to the code following the .endif directive. See Assemble Conditional Blocks for more information on the .if/ .elseif/.else/.endif directives.
The .loop/.break/.endloop directives enable you to assemble a code block repeatedly. The format of a repeatable block is:
.loop [well-defined expression] | |
[.break [well-defined expression]] | |
.endloop |
The .loop directive's optional well-defined expression evaluates to the loop count (the number of loops to be performed). If the expression is omitted, the loop count defaults to 1024 unless the assembler encounters a .break directive with an expression that is true (nonzero). See Assemble Conditional Blocks Repeatedly for more information on the .loop/.break/.endloop directives.
The .break directive and its expression are optional in repetitive assembly. If the expression evaluates to false, the loop continues. The assembler breaks the loop when the .break expression evaluates to true or when the .break expression is omitted. When the loop is broken, the assembler continues with the code after the .endloop directive. For more information, see Section 5.8.
Example 6-10 , Example 6-11, and Example 6-12 show the .loop/.break/ .endloop directives, properly nested conditional assembly directives, and built-in substitution symbol functions used in a conditional assembly code block.
Example 6-10 The .loop/.break/.endloop Directives
.asg 1,x
.loop
.break (x == 10) ; if x == 10, quit loop/break with expression
.eval x+1,x
.endloop
Example 6-11 Nested Conditional Assembly Directives
.asg 1,x
.loop
.if (x == 10) ; if x == 10, quit loop
.break (x == 10) ; force break
.endif
.eval x+1,x
.endloop
Example 6-12 Built-In Substitution Symbol Functions in a Conditional Assembly Code Block
.fcnolist
*
*Double Add or Subtract
*
DBL .macro ABC, dsth, dstl, srch, srcl ; add or subtract double
.if $$symcmp(ABC,"+")
ADDS dstl, dstl, srcl ; add double
ADC dsth, dsth, srch
.elseif $$symcmp(ABC,"-")
SUBS dstl, dstl, srcl ; subtract double
SUBS dsth, dsth, srch
.else
.emsg "Incorrect Operator Parameter" .endif
.endm
*Macro Call
DBL -, R4, R5, R6, R7
6.6 Using Labels in Macros
All labels in an assembly language program must be unique. This includes labels in macros. If a macro is expanded more than once, its labels are defined more than once. Defining a label more than once is illegal. The macro language provides a method of defining labels in macros so that the labels are unique. Simply follow each label with a question mark, and the assembler replaces the question mark with a period followed by a unique number. When the macro is expanded, you do not see the unique number in the listing file. Your label appears with the question mark as it did in the macro definition. You cannot declare this label as global. See Section 4.8.3 for more about labels.
The syntax for a unique label is:
label? |
Example 6-13 shows unique label generation in a macro. The maximum label length is shortened to allow for the unique suffix. For example, if the macro is expanded fewer than 10 times, the maximum label length is 126 characters. If the macro is expanded from 10 to 99 times, the maximum label length is 125. The label with its unique suffix is shown in the cross-listing file. To obtain a cross-listing file, invoke the assembler with the --cross_reference option (see Section 4.3).
Example 6-13 Unique Labels in a Macro
1 ; define macro to find minimum
2 MIN .macro dst, src1, src2
3 CMP src1, src2
4 BCC m1?
5 MOV dst, src1
6 B m2?
7
8 m1? MOV dst, src2
9 m2?
10 .endm
11
12 ; call macro
13 00000000 .state16
14 00000000 MIN r4, r1, r2
1 00000000 4291 CMP r1, r2
1 00000002 D301 BCC m1?
1 00000004 1C0C MOV r4, r1
1 00000006 E000 B m2?
1
1 00000008 1C14 m1? MOV r4, r2
1 0000000a m2?
6.7 Producing Messages in Macros
The macro language supports three directives that enable you to define your own assembly-time error and warning messages. These directives are especially useful when you want to create messages specific to your needs. The last line of the listing file shows the error and warning counts. These counts alert you to problems in your code and are especially useful during debugging.
.emsg | sends error messages to the listing file. The .emsg directive generates errors in the same manner as the assembler, incrementing the error count and preventing the assembler from producing an object file. |
.mmsg | sends assembly-time messages to the listing file. The .mmsg directive functions in the same manner as the .emsg directive but does not set the error count or prevent the creation of an object file. |
.wmsg | sends warning messages to the listing file. The .wmsg directive functions in the same manner as the .emsg directive, but it increments the warning count and does not prevent the generation of an object file. |
Macro comments are comments that appear in the definition of the macro but do not show up in the expansion of the macro. An exclamation point in column 1 identifies a macro comment. If you want your comments to appear in the macro expansion, precede your comment with an asterisk or semicolon.
Example 6-14 shows user messages in macros and macro comments that do not appear in the macro expansion.
For more information about the .emsg, .mmsg, and .wmsg assembler directives, see Define Messages.
Example 6-14 Producing Messages in a Macro
1 MUL_I .macro x,y
2 .if ($$symlen(x) ==0)
3 .emsg "ERROR -- Missing Parameter" 4 .mexit
5 .elseif ($$symlen(y) == 0)
6 .emsg "ERROR -- Missing Parameter" 7 .mexit
8 .else
9 MOV R1, x
10 MOV R2, y
11 MUL R0, R1, R2
12 .endif
13 .endm
14
15 00000000 MUL_I #50, #51
1 .if ($$symlen(x) ==0)
1 .emsg "ERROR -- Missing Parameter"1 .mexit
1 .elseif ($$symlen(y) == 0)
1 .emsg "ERROR -- Missing Parameter"1 .mexit
1 .else
1 00000000 E3A01032 MOV R1, #50
1 00000004 E3A02033 MOV R2, #51
1 00000008 E0000291 MUL R0, R1, R2
1 .endif
16
17 0000000c MUL_I
1 .if ($$symlen(x) ==0)
1 .emsg "ERROR -- Missing Parameter" ***** USER ERROR ***** - : ERROR -- Missing Parameter
1 .mexit
1 Error, No Warnings
6.8 Using Directives to Format the Output Listing
Macros, substitution symbols, and conditional assembly directives may hide information. You may need to see this hidden information, so the macro language supports an expanded listing capability.
By default, the assembler shows macro expansions and false conditional blocks in the list output file. You may want to turn this listing off or on within your listing file. Four sets of directives enable you to control the listing of this information:
|
||
.mlist | expands macros and .loop/.endloop blocks. The .mlist directive prints all code encountered in those blocks. | |
.mnolist |
suppresses the listing of macro expansions and .loop/ .endloop blocks. | |
For macro and loop expansion listing, .mlist is the default. | ||
|
||
.fclist | causes the assembler to include in the listing file all conditional blocks that do not generate code (false conditional blocks). Conditional blocks appear in the listing exactly as they appear in the source code. | |
.fcnolist | suppresses the listing of false conditional blocks. Only the code in conditional blocks that actually assemble appears in the listing. The .if, .elseif, .else, and .endif directives do not appear in the listing. | |
For false conditional block listing, .fclist is the default. | ||
|
||
.sslist | expands substitution symbols in the listing. This is useful for debugging the expansion of substitution symbols. The expanded line appears below the actual source line. | |
.ssnolist | turns off substitution symbol expansion in the listing. | |
For substitution symbol expansion listing, .ssnolist is the default. | ||
|
||
.drlist | causes the assembler to print to the listing file all directive lines. | |
.drnolist | suppresses the printing of certain directives in the listing file. These directives are .asg, .eval, .var, .sslist, .mlist, .fclist, .ssnolist, .mnolist, .fcnolist, .emsg, .wmsg, .mmsg, .length, .width, and .break. | |
For directive listing, .drlist is the default. |
6.9 Using Recursive and Nested Macros
The macro language supports recursive and nested macro calls. This means that you can call other macros in a macro definition. You can nest macros up to 32 levels deep. When you use recursive macros, you call a macro from its own definition (the macro calls itself).
When you create recursive or nested macros, you should pay close attention to the arguments that you pass to macro parameters because the assembler uses dynamic scoping for parameters. This means that the called macro uses the environment of the macro from which it was called.
Example 6-15 shows nested macros. The y in the in_block macro hides the y in the out_block macro. The x and z from the out_block macro, however, are accessible to the in_block macro.
Example 6-15 Using Nested Macros
in_block .macro y,a
. ; visible parameters are y,a and x,z from the calling macro
.endm
out_block .macro x,y,z
. ; visible parameters are x,y,z
.
in_block x,y ; macro call with x and y as arguments
.
.
.endm
out_block ; macro call
Example 6-16 shows recursive and fact macros. The fact macro produces assembly code necessary to calculate the factorial of n, where n is an immediate value. The result is placed in data memory address loc. The fact macro accomplishes this by calling fact1, which calls itself recursively.
Example 6-16 Using Recursive Macros
fact .macro N, loc ; N is an integer constant. Register loc address = N!
.if N < 2 ; 0! = 1! = 1
MOV loc, #1
.else
MOV loc, #N ; N >= 2 so, store N in loc.
.eval -1, N ; Decrement N, and do the factorial of N - 1.
fact1 ; Call fact with current environment.
.endm
fact1 .macro
.if N > 1
MOV R0, #N ; N > 1 so, store N in R0.
MUL loc, R0, loc ; Multiply present factorial by present position.
.eval N - 1, N ; Decrement position.
fact1 ; Recursive call.
.endif
.endm
6.10 Macro Directives Summary
The directives listed in Table 6-2 through Table 6-6 can be used with macros. The .macro, .mexit, .endm and .var directives are valid only with macros; the remaining directives are general assembly language directives.
Table 6-2 Creating Macros
See | |||
---|---|---|---|
Mnemonic and Syntax | Description | Macro Use | Directive |
.endm | End macro definition | Section 6.2 | .endm |
macname .macro [parameter1 ][,... , parametern ] | Define macro by macname | Section 6.2 | .macro |
.mexit | Go to .endm | Section 6.2 | Section 6.2 |
.mlib filename | Identify library containing macro definitions | Section 6.4 | .mlib |
Table 6-3 Manipulating Substitution Symbols
See | |||
---|---|---|---|
Mnemonic and Syntax | Description | Macro Use | Directive |
.asg ["]character string["], substitution symbol | Assign character string to substitution symbol | Section 6.3.1 | .asg |
.eval well-defined expression, substitution symbol | Perform arithmetic on numeric substitution symbols | Section 6.3.1 | .eval |
.var sym1 [,sym2 , ...,symn ] | Define local macro symbols | Section 6.3.6 | .var |
Table 6-4 Conditional Assembly
See | |||
---|---|---|---|
Mnemonic and Syntax | Description | Macro Use | Directive |
.break [well-defined expression] | Optional repeatable block assembly | Section 6.5 | .break |
.endif | End conditional assembly | Section 6.5 | .endif |
.endloop | End repeatable block assembly | Section 6.5 | .endloop |
.else | Optional conditional assembly block | Section 6.5 | .else |
.elseif well-defined expression | Optional conditional assembly block | Section 6.5 | .elseif |
.if well-defined expression | Begin conditional assembly | Section 6.5 | .if |
.loop [well-defined expression] | Begin repeatable block assembly | Section 6.5 | .loop |
Table 6-5 Producing Assembly-Time Messages
See | |||
---|---|---|---|
Mnemonic and Syntax | Description | Macro Use | Directive |
.emsg | Send error message to standard output | Section 6.7 | .emsg |
.mmsg | Send assembly-time message to standard output | Section 6.7 | .mmsg |
.wmsg | Send warning message to standard output | Section 6.7 | .wmsg |
Table 6-6 Formatting the Listing
See | |||
---|---|---|---|
Mnemonic and Syntax | Description | Macro Use | Directive |
.fclist | Allow false conditional code block listing (default) | Section 6.8 | .fclist |
.fcnolist | Suppress false conditional code block listing | Section 6.8 | .fcnolist |
.mlist | Allow macro listings (default) | Section 6.8 | .mlist |
.mnolist | Suppress macro listings | Section 6.8 | .mnolist |
.sslist | Allow expanded substitution symbol listing | Section 6.8 | .sslist |
.ssnolist | Suppress expanded substitution symbol listing (default) | Section 6.8 | .ssnolist |
Copyright© 2018, Texas Instruments Incorporated. An IMPORTANT NOTICE for this document addresses availability, warranty, changes, use in safety-critical applications, intellectual property matters and other important disclaimers.