The remainder of this chapter is a reference. Generally, the directives are organized alphabetically, one directive per topic. Related directives (such as .if/.else/.endif), however, are presented together in one topic.
.align [size in bytes]
The .align directive aligns the section program counter (SPC) on the next boundary, depending on the size in bytes parameter. The size can be any power of 2, although only certain values are useful for alignment. An operand of 1 aligns the SPC on the next byte boundary, and this is the default if no size in bytes is given. The size in bytes must equal a power of 2; the value must be between 1 and 32,768, inclusive. The assembler assembles words containing null values (0) up to the next size in bytes boundary:
1 | aligns SPC to byte boundary |
2 | aligns SPC to halfword boundary |
4 | aligns SPC to word boundary |
8 | aligns SPC to doubleword boundary |
Using the .align directive has two effects:
This example shows several types of alignment, including .align 2, .align 8, and a default .align.
1 00000000 00000004 .byte 4
2 .align 2
3 00000002 00000045 .string "Errorcnt"
00000003 00000072
00000004 00000072
00000005 0000006F
00000006 00000072
00000007 00000063
00000008 0000006E
00000009 00000074
4 .align
5 00000008 0003746E .field 3,3
6 00000008 002B746E .field 5,4
7 .align 2
8 0000000c 00000003 .field 3,3
9 .align 8
10 00000010 00000005 .field 5,4
11 .align
12 00000011 00000004 .byte 4
.asg "character string",substitution symbol
.define "character string",substitution symbol
.eval expression,substitution symbol
The .asg and .define directives assign character strings to substitution symbols. Substitution symbols are stored in the substitution symbol table. The .asg directive can be used in many of the same ways as the .set directive, but while .set assigns a constant value (which cannot be redefined) to a symbol, .asg assigns a character string (which can be redefined) to a substitution symbol.
The .define directive functions in the same manner as the .asg directive, except that .define disallows creation of a substitution symbol that has the same name as a register symbol or mnemonic. It does not create a new symbol name space in the assembler, rather it uses the existing substitution symbol name space. The .define directive is used to prevent corruption of the assembly environment when converting C/C++ headers. See Section 11 for more information about using C/C++ headers in assembly source.
The .eval directive performs arithmetic on substitution symbols, which are stored in the substitution symbol table. This directive evaluates the expression and assigns the string value of the result to the substitution symbol. The .eval directive is especially useful as a counter in .loop/.endloop blocks.
See the .unasg/.undefine topic for information on turning off a substitution symbol.
This example shows how .asg and .eval can be used.
1 .sslist ; show expanded substitution symbols
2
3 .asg *+B14(100), GLOB100
4 .asg *+B15(4), ARG0
5
6 00000000 003B22E4 LDW GLOB100,A0
# LDW *+B14(100),A0
7 00000004 00BC22E4 LDW ARG0,A1
# LDW *+B15(4),A1
8 00000008 00006000 NOP 4
9 0000000c 010401E0 ADD A0,A1,A2
10
11 .asg 0,x
12 .loop 5
13 .word 100*x
14 .eval x+1,x
15 .endloop
1 00000010 00000000 .word 100*x
# .word 100*0
1 .eval x+1,x
# .eval 0+1,x
1 00000014 00000064 .word 100*x
# .word 100*1
1 .eval x+1,x
# .eval 1+1,x
1 00000018 000000C8 .word 100*x
# .word 100*2
1 .eval x+1,x
# .eval 2+1,x
1 0000001c 0000012C .word 100*x
# .word 100*3
1 .eval x+1,x
# .eval 3+1,x
1 00000020 00000190 .word 100*x
# .word 100*4
1 .eval x+1,x
# .eval 4+1,x
symbol .asmfunc [stack_usage(num)]
.endasmfunc
The .asmfunc and .endasmfunc directives mark function boundaries. These directives are used with the compiler -g option (--symdebug:dwarf) to allow assembly code sections to be debugged in the same manner as C/C++ functions.
You should not use the same directives generated by the compiler (see Section A) to accomplish assembly debugging; those directives should be used only by the compiler to generate symbolic debugging information for C/C++ source files.
The symbol is a label that must appear in the label field.
The .asmfunc directive has an optional parameter, stack_usage, which indicates that the function may use up to num bytes.
Consecutive ranges of assembly code that are not enclosed within a pair of .asmfunc and .endasmfunc directives are given a default name in the following format:
$filename:beginning source line:ending source line$
This example generates debug information for the user_func section.
1 00000000 .sect ".text"
2 .global userfunc
3 .global _printf
4
5 userfunc: .asmfunc stack_usage(16)
6 00000000 00000010! CALL .S1 _printf
7 00000004 01BC94F6 STW .D2T2 B3,*B15--(16)
8 00000008 01800E2A' MVKL .S2 RL0,B3
9 0000000c 01800028+ MVKL .S1 SL1+0,A3
10 00000010 01800068+ MVKH .S1 SL1+0,A3
11
12 00000014 01BC22F5 STW .D2T1 A3,*+B15(4)
13 00000018 0180006A' || MVKH .S2 RL0,B3
14
15 0000001c 01BC92E6 RL0: LDW .D2T2 *++B15(16),B3
16 00000020 020008C0 ZERO .D1 A4
17 00000024 00004000 NOP 3
18 00000028 000C0362 RET .S2 B3
19 0000002c 00008000 NOP 5
20 .endasmfunc
21
22 00000000 .sect ".const"
23 00000000 00000048 SL1: .string "Hello World!",10,0
00000001 00000065
00000002 0000006C
00000003 0000006C
00000004 0000006F
00000005 00000020
00000006 00000057
00000007 0000006F
00000008 00000072
00000009 0000006C
0000000a 00000064
0000000b 00000021
0000000c 0000000A
0000000d 00000000
.bitsvalue1[, ... ,valuen]
The .bits directive places one or more values into consecutive bits of the current section.
The .bits directive is similar to the .field directive (see .field topic ). However, the .bits directive does not allow you to specify the number of bits to fill or increment the SPC.
.bss symbol,size in bytes[, alignment[, bank offset]]
The .bss directive reserves space for variables in the .bss section. This directive is usually used to allocate space in RAM.
For more information about sections, see Section 2.
In this example, the .bss directive allocates space for a variable, array. The symbol array points to 100 bytes of uninitialized space (at .bss SPC = 0). Symbols declared with the .bss directive can be referenced in the same manner as other symbols and can also be declared global.
1 *******************************************
2 ** Start assembling into .text section. **
3 *******************************************
4 00000000 .text
5 00000000 008001A0 MV A0,A1
6
7 *******************************************
8 ** Allocate 100 bytes in .bss. **
9 *******************************************
10 00000000 .bss array,100
11
12 *******************************************
13 ** Still in .text **
14 *******************************************
15 00000004 010401A0 MV A1,A2
16
17 *******************************************
18 ** Declare external .bss symbol **
19 *******************************************
20 .global array
.bytevalue1[, ... ,valuen]
.ubytevalue1[, ... ,valuen]
.charvalue1[, ... ,valuen]
.ucharvalue1[, ... ,valuen]
The .byte, .ubyte, .char, and .uchardirectives place one or more values into consecutive bytes of the current section. A value can be one of the following:
With little-endian ordering, the first byte occupies the eight least significant bits of a full 32-bit word. The second byte occupies bits eight through 15 while the third byte occupies bits 16 through 23. The assembler truncates values greater than eight bits.
If you use a label, it points to the location of the first byte that is initialized.
When you use these directives in a .struct/.endstruct sequence, they define a member's size; they do not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
In this example, 8-bit values (10, -1, abc, and a) are placed into consecutive bytes in memory with .byte. Also, 8-bit values (8, -3, def, and b) are placed into consecutive bytes in memory with .char. The label STRX has the value 0h, which is the location of the first initialized byte. The label STRY has the value 6h, which is the first byte initialized by the .char directive.
1 00000000 0000000A STRX .byte 10,-1,"abc",'a'
00000001 000000FF
00000002 00000061
00000003 00000062
00000004 00000063
00000005 00000061
2 00000006 00000008 STRY .char 8,-3,"def",'b'
Single Line:
.cdecls [options,] "filename"[, "filename2"[,...]]
Multiple Lines:
.cdecls [options]
%{
/*---------------------------------------------------------------------------------*/
/* C/C++ code - Typically a list of #includes and a few defines */
/*---------------------------------------------------------------------------------*/
%}
The .cdecls directive allows programmers in mixed assembly and C/C++ environments to share C headers containing declarations and prototypes between the C and assembly code. Any legal C/C++ can be used in a .cdecls block and the C/C++ declarations cause suitable assembly to be generated automatically, allowing you to reference the C/C++ constructs in assembly code; such as calling functions, allocating space, and accessing structure members; using the equivalent assembly mechanisms. While function and variable definitions are ignored, most common C/C++ elements are converted to assembly, for instance: enumerations, (non-function-like) macros, function and variable prototypes, structures, and unions.
The .cdecls options control whether the code is treated as C or C++ code; and how the .cdecls block and converted code are presented. Options must be separated by commas; they can appear in any order:
C | Treat the code in the .cdecls block as C source code (default). | |
CPP | Treat the code in the .cdecls block as C++ source code. This is the opposite of the C option. | |
NOLIST | Do not include the converted assembly code in any listing file generated for the containing assembly file (default). | |
LIST | Include the converted assembly code in any listing file generated for the containing assembly file. This is the opposite of the NOLIST option. | |
NOWARN | Do not emit warnings on STDERR about C/C++ constructs that cannot be converted while parsing the .cdecls source block (default). | |
WARN | Generate warnings on STDERR about C/C++ constructs that cannot be converted while parsing the .cdecls source block. This is the opposite of the NOWARN option. |
In the single-line format, the options are followed by one or more filenames to include. The filenames and options are separated by commas. Each file listed acts as if #include "filename" was specified in the multiple-line format.
In the multiple-line format, the line following .cdecls must contain the opening .cdecls block indicator %{. Everything after the %{, up to the closing block indicator %}, is treated as C/C++ source and processed. Ordinary assembler processing then resumes on the line following the closing %}.
The text within %{ and %} is passed to the C/C++ compiler to be converted into assembly language. Much of C language syntax, including function and variable definitions as well as function-like macros, is not supported and is ignored during the conversion. However, all of what traditionally appears in C header files is supported, including function and variable prototypes; structure and union declarations; non-function-like macros; enumerations; and #defines.
The resulting assembly language is included in the assembly file at the point of the .cdecls directive. If the LIST option is used, the converted assembly statements are printed in the listing file.
The assembly resulting from the .cdecls directive is treated similarly to a .include file. Therefore the .cdecls directive can be nested within a file being copied or included. The assembler limits nesting to ten levels; the host operating system may set additional restrictions. The assembler precedes the line numbers of copied files with a letter code to identify the level of copying. An A indicates the first copied file, B indicates a second copied file, etc.
The .cdecls directive can appear anywhere in an assembly source file, and can occur multiple times within a file. However, the C/C++ environment created by one .cdecls is not inherited by a later .cdecls; the C/C++ environment starts new for each .cdecls.
See Section 11 for more information on setting up and using the .cdecls directive with C header files.
In this example, the .cdecls directive is used call the C header.h file.
C header file:
#define WANT_ID 10
#define NAME "John\n"
extern int a_variable;
extern float cvt_integer(int src);
struct myCstruct { int member_a; float member_b; };
enum status_enum { OK = 1, FAILED = 256, RUNNING = 0 };
Source file:
.cdecls C,LIST,"myheader.h"
size: .int $sizeof(myCstruct)
aoffset: .int myCstruct.member_a
boffset: .int myCstruct.member_b
okvalue: .int status_enum.OK
failval: .int status_enum.FAILED
.if $defined(WANT_ID)
id .cstring NAME
.endif
Listing File:
1 .cdecls C,LIST,"myheader.h"
A 1 ; ------------------------------------------
A 2 ; Assembly Generated from C/C++ Source Code
A 3 ; ------------------------------------------
A 4
A 5 ; =========== MACRO DEFINITIONS ===========
A 6 .define "10",WANT_ID
A 7 .define """John\n""",NAME
A 8
A 9 ; =========== TYPE DEFINITIONS ===========
A 10 status_enum .enum
A 11 00000001 OK .emember 1
A 12 00000100 FAILED .emember 256
A 13 00000000 RUNNING .emember 0
A 14 .endenum
A 15
A 16 myCstruct .struct 0,4
17 ; struct size=(8 bytes|64 bits), alignment=4
A 18 00000000 member_a .field 32
19 ; int member_a - offset 0 bytes, size (4 bytes|32 bits)
A 20 00000004 member_b .field 32
21 ; float member_b - offset 4 bytes, size (4 bytes|32 bits)
A 22 00000008 .endstruct
23 ; final size=(8 bytes|64 bits)
A 24
A 25 ; =========== EXTERNAL FUNCTIONS ===========
A 26 .global _cvt_integer
A 27
A 28 ; =========== EXTERNAL VARIABLES ===========
A 29 .global _a_variable
2 00000000 00000008 size: .int $sizeof(myCstruct)
3 00000004 00000000 aoffset: .int myCstruct.member_a
4 00000008 00000004 boffset: .int myCstruct.member_b
5 0000000c 00000001 okvalue: .int status_enum.OK
6 00000010 00000100 failval: .int status_enum.FAILED
7 .if $defined(WANT_ID)
8 00000014 0000004A id .cstring NAME
00000015 0000006F
00000016 00000068
00000017 0000006E
00000018 0000000A
00000019 00000000
9 .endif
.common symbol,size in bytes[, alignment]
.common symbol,structure tag[, alignment]
The .common directive creates a common symbol in a common block, rather than placing the variable in a memory section.
This directive is used by the compiler when the --common option is enabled (the default), which causes uninitialized file scope variables to be emitted as common symbols. The benefit of common symbols is that generated code can remove unused variables that would otherwise increase the size of the .bss section. (Uninitialized variables of a size larger than 32 bytes are separately optimized through placement in separate subsections that can be omitted from a link.) This optimization happens for C/C++ code by default unless you use the --common=off compiler option.
Common symbols are symbols that are placed in the symbol table of an ELF object file. They represent an uninitialized variable. Common symbols do not reference a section. (In contrast, initialized variables need to reference a section that contains the initialized data.) The value of a common symbol is its required alignment; it has no address and stores no address. While symbols for an uninitialized common block can appear in executable object files, common symbols may only appear in relocatable object files. Common symbols are preferred over weak symbols. See the section on the "Symbol Table" in the System V ABI specification for more about common symbols.
When object files containing common symbols are linked, space is reserved in an uninitialized section for each common symbol. A symbol is created in place of the common symbol to refer to its reserved location.
.copy"filename"
.include"filename"
The .copy and .include directives tell the assembler to read source statements from a different file. The statements that are assembled from a copy file are printed in the assembly listing. The statements that are assembled from an included file are not printed in the assembly listing, regardless of the number of .list/.nolist directives assembled.
When a .copy or .include directive is assembled, the assembler:
The filename is a required parameter that names a source file. It is enclosed in double quotes and must follow operating system conventions.
You can specify a full pathname (for example, /320tools/file1.asm). If you do not specify a full pathname, the assembler searches for the file in:
For more information about the --include_path option and C6X_A_DIR, see Section 4.5. For more information about C6X_C_DIR, see the TMS320C6000 Optimizing Compiler User's Guide.
The .copy and .include directives can be nested within a file being copied or included. The assembler limits nesting to 32 levels; the host operating system may set additional restrictions. The assembler precedes the line numbers of copied files with a letter code to identify the level of copying. A indicates the first copied file, B indicates a second copied file, etc.
In this example, the .copy directive is used to read and assemble source statements from other files; then, the assembler resumes assembling into the current file.
The original file, copy.asm, contains a .copy statement copying the file byte.asm. When copy.asm assembles, the assembler copies byte.asm into its place in the listing (note listing below). The copy file byte.asm contains a .copy statement for a second file, word.asm.
When it encounters the .copy statement for word.asm, the assembler switches to word.asm to continue copying and assembling. Then the assembler returns to its place in byte.asm to continue copying and assembling. After completing assembly of byte.asm, the assembler returns to copy.asm to assemble its remaining statement.
copy.asm
(source file) |
byte.asm
(first copy file) |
word.asm
(second copy file) |
---|---|---|
.space 29
|
** In byte.asm
|
** In word.asm
|
Listing file:
1 00000000 .space 29
2 .copy "byte.asm"
A 1 ** In byte.asm
A 2 0000001d 00000020 .byte 32,1+ 'A'
0000001e 00000042
A 3 .copy "word.asm"
B 1 ** In word.asm
B 2 00000020 0000ABCD .word 0ABCDh, 56q
00000024 0000002E
A 4 ** Back in byte.asm
A 5 00000028 0000006A .byte 67h + 3q
3
4 ** Back in original file
5 00000029 00000064 .string "done"
0000002a 0000006F
0000002b 0000006E
0000002c 00000065
In this example, the .include directive is used to read and assemble source statements from other files; then, the assembler resumes assembling into the current file. The mechanism is similar to the .copy directive, except that statements are not printed in the listing file.
include.asm
(source file) |
byte2.asm
(first copy file) |
word2.asm
(second copy file) |
---|---|---|
.space 29
|
** In byte2.asm
|
** In word2.asm
|
Listing file:
1 00000000 .space 29
2 .include "byte2.asm"
3
4 ** Back in original file
5 00000029 00000064 .string "done"
0000002a 0000006F
0000002b 0000006E
0000002c 00000065
[stag] .cstruct|.cunion [expr]
[mem0] element [expr0]
[mem1] element [expr1]
. . .
. . .
[memn] .tag stag [exprn]
[memN] element [exprN]
[size] .endstruct|.endunion
label .tag stag
The .cstruct and .cunion directives have been added to support ease of sharing of common data structures between assembly and C code. The .cstruct and .cunion directives can be used exactly like the existing .struct and .union directives except that they are guaranteed to perform data layout matching the layout used by the C compiler for C struct and union data types.
In particular, the .cstruct and .cunion directives force the same alignment and padding as used by the C compiler when such types are nested within compound data structures.
The .endstruct directive terminates the structure definition. The .endunion directive terminates the union definition.
The .tag directive gives structure characteristics to a label, simplifying the symbolic representation and providing the ability to define structures that contain other structures. The .tag directive does not allocate memory. The structure tag (stag) of a .tag directive must have been previously defined.
Following are descriptions of the parameters used with the .struct, .endstruct, and .tag directives:
This example illustrates a structure in C that will be accessed in assembly code.
typedef struct STRUCT1
; { int i0; /* offset 0 */
; short s0; /* offset 4 */
; } struct1; /* size 8, alignment 4 */
;
; typedef struct STRUCT2
; { struct1 st1; /* offset 0 */
; short s1; /* offset 8 */
; } struct2; /* size 12, alignment 4 */
;
; The structure will get the following offsets once the C compiler lays out the structure
; elements according to the C standard rules:
;
; offsetof(struct1, i0) = 0
; offsetof(struct1, s0) = 4
; sizeof(struct1) = 8
; offsetof(struct2, s1) = 0
; offsetof(struct2, i1) = 8
; sizeof(struct2) = 12
;
; Attempts to replicate this structure in assembly using the .struct/.union directives will not
; create the correct offsets because the assembler tries to use the most compact arrangement:
struct1 .struct
i0 .int ; bytes 0-3
s0 .short ; bytes 4-5
struct1len .endstruct ; size 6, alignment 4
struct2 .struct
st1 .tag struct1 ; bytes 0-5
s1 .short ; bytes 6-7
endstruct2 .endstruct ; size 8, alignment 4
.sect "data1"
.word struct1.i0 ; 0
.word struct1.s0 ; 4
.word struct1len ; 6
.sect "data2"
.word struct2.st1 ; 0
.word struct2.s1 ; 6
.word endstruct2 ; 8
;
; The .cstruct/.cunion directives calculate offsets in the same manner as the C compiler. The resulting
; assembly structure can be used to access the elements of the C structure. Compare the difference
; in the offsets of those structures defined via .struct above and the offsets for the C code.
cstruct1 .cstruct
i0 .int ; bytes 0-3
s0 .short ; bytes 4-5
cstruct1len .endstruct ; size 8, alignment 4
cstruct2 .cstruct
st1 .tag cstruct1 ; bytes 0-7
s1 .short ; bytes 8-9
cendstruct2 .endstruct ; size 12, alignment 4
.sect "data3"
.word cstruct1.i0, struct1.i0 ; 0
.word cstruct1.s0, struct1.s0 ; 4
.word cstruct1len, struct1len ; 8
.sect "data4"
.word cstruct2.st1, struct2.st1 ; 0
.word cstruct2.s1, struct2.s1 ; 8
.word cendstruct2, endstruct2 ; 12
.data
The .data directive sets .data as the current section; the lines that follow will be assembled into the .data section. The .data section is normally used to contain tables of data or preinitialized variables.
For more information about sections, see Section 2.
In this example, code is assembled into the .data and .text sections.
1 ***********************************************
2 ** Reserve space in .data **
3 ***********************************************
4 00000000 .data
5 00000000 .space 0CCh
6
7 ***********************************************
8 ** Assemble into .text **
9 ***********************************************
10 00000000 .text
11 00000000 00800358 ABS A0,A1
12
13 ***********************************************
14 ** Assemble into .data **
15 ***********************************************
16 000000cc table: .data
17 000000cc FFFFFFFF .word -1
18 000000d0 000000FF .byte 0FFh
19
20 ***********************************************
21 ** Assemble into .text **
22 ***********************************************
23 00000004 .text
24 00000004 008001A0 MV A0,A1
25
26 ***********************************************
27 ** Resume assembling into the .data section **
28 ***********************************************
29 000000d1 .data
30 000000d4 00000000 coeff .word 00h,0ah,0bh
000000d8 0000000A
000000dc 0000000B
.doublevalue1 [, ... ,valuen]
The .double directive places the IEEE double-precision floating-point representation of one or more floating-point values into the current section. Each value must be an absolute constant expression with an arithmetic type or a symbol equated to an absolute constant expression with an arithmetic type. Each constant is converted to a floating-point value in IEEE double-precision 64-bit format. Double-precision floating point constants are aligned to a double word boundary.
The 64-bit value is stored in the format shown in Figure 5-5.
When you use .double in a .struct/.endstruct sequence, .double defines a member's size; it does not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
This example shows the .double directive.
1 00000000 2C280291 .double -2.0e25
00000004 C5308B2A
2 00000008 00000000 .double 6
0000000c 40180000
3 00000010 00000000 .double 456
00000014 407C8000
.drlist
.drnolist
Two directives enable you to control the printing of assembler directives to the listing file:
The .drlist directive enables the printing of all directives to the listing file.
The .drnolist directive suppresses the printing of the following directives to the listing file. The .drnolist directive has no affect within macros.
|
|
|
By default, the assembler acts as if the .drlist directive had been specified.
This example shows how .drnolist inhibits the listing of the specified directives.
Source file:
.length 65
.width 85
.asg 0, x
.loop 2
.eval x+1, x
.endloop
.drnolist
.length 55
.width 95
.asg 1, x
.loop 3
.eval x+1, x
.endloop
Listing file:
3 .asg 0, x
4 .loop 2
5 .eval x+1, x
6 .endloop
1 .eval 0+1, x
1 .eval 1+1, x
7
8 .drnolist
12 .loop 3
13 .eval x+1, x
14 .endloop
.elfsym name, SYM_SIZE(size)
The .elfsym directive provides additional information for symbols in the ELF format. This directive is designed to convey different types of information, so the type, data pair is used to represent each type. Currently, this directive only supports the SYM_SIZE type.
SYM_SIZE indicates the allocation size (in bytes) of the symbol indicated by name.
This example shows the use of the ELF symbol information directive.
.sect ".examp"
.alignment 4
.elfsym ex_sym, SYM_SIZE(4)
ex_sym:
.word 0
.emsg string
.mmsg string
.wmsg string
These directives allow you to define your own error and warning messages. When you use these directives, the assembler tracks the number of errors and warnings it encounters and prints these numbers on the last line of the listing file.
The .emsg directive sends an error message to the standard output device in the same manner as the assembler. It increments the error count and prevents the assembler from producing an object file.
The .mmsg directive sends an assembly-time message to the standard output device in the same manner as the .emsg and .wmsg directives. It does not, however, set the error or warning counts, and it does not prevent the assembler from producing an object file.
The .wmsg directive sends a warning message to the standard output device in the same manner as the .emsg directive. It increments the warning count rather than the error count, however. It does not prevent the assembler from producing an object file.
This example sends the message ERROR -- MISSING PARAMETER to the standard output device.
Source file:
.global PARAM
MSG_EX .macro parm1
.if $symlen(parm1) = 0
.emsg "ERROR -- MISSING PARAMETER"
.else
MVK parm1, A1
.endif
.endm
MSG_EX PARAM
MSG_EX
Listing file:
1 .global PARAM
2 MSG_EX .macro parm1
3 .if $symlen(parm1) = 0
4 .emsg "ERROR -- MISSING PARAMETER"
5 .else
6 MVK parm1, A1
7 .endif
8 .endm
9
10 00000000 MSG_EX PARAM
1 .if $symlen(parm1) = 0
1 .emsg "ERROR -- MISSING PARAMETER"
1 .else
1 00000000 00800028! MVK PARAM, A1
1 .endif
11
12 00000004 MSG_EX
1 .if $symlen(parm1) = 0
1 .emsg "ERROR -- MISSING PARAMETER"
***** USER ERROR ***** - : ERROR -- MISSING PARAMETER
1 .else
1 MVK parm1, A1
1 .endif
1 Error, No Warnings
In addition, the following messages are sent to standard output by the assembler:
"t.asm", ERROR! at line 10: [ ***** USER ERROR ***** - ] ERROR -- MISSING PARAMETER
.emsg "ERROR -- MISSING PARAMETER"
1 Assembly Error, No Assembly Warnings
Errors in Source - Assembler Aborted
.end
The .end directive is optional and terminates assembly. The assembler ignores any source statements that follow a .end directive. If you use the .end directive, it must be the last source statement of a program.
This directive has the same effect as an end-of-file character. You can use .end when you are debugging and you want to stop assembling at a specific point in your code.
NOTE
Ending a MacroDo not use the .end directive to terminate a macro; use the .endm macro directive instead.
This example shows how the .end directive terminates assembly. Any source statements that follow the .end directive are ignored by the assembler.
Source file:
start: .text
ZERO A0
ZERO A1
ZERO A3
.end
ZERO A4
Listing file:
1 00000000 start: .text
2 00000000 000005E0 ZERO A0
3 00000004 008425E0 ZERO A1
4 00000008 018C65E0 ZERO A3
5 .end
.farcommon symbol,size in bytes[, alignment]
.farcommon symbol,structure tag[, alignment]
.nearcommon symbol,size in bytes[, alignment]
.nearcommon symbol,structure tag[, alignment]
The .farcommon and .nearcommon directives create a common symbol in a common block, rather than placing variables in a section. The .farcommon directive places the symbol in far memory, and the .nearcommon directive places the symbol in near memory.
A common symbol cannot be created for a symbol that has a memory bank specification, for example because the DATA_MEM_BANK pragma was used to align the variable.
These directives are used by the compiler when the --common option is enabled (the default), which causes uninitialized file scope variables to be emitted as common symbols. The benefit of common symbols is that generated code can remove unused variables that would otherwise increase the size of the .bss section. (Uninitialized variables of a size larger than 32 bytes are separately optimized through placement in separate subsections that can be omitted from a link.) This optimization happens for C/C++ code by default unless you use the --common=off compiler option.
.fclist
.fcnolist
Two directives enable you to control the listing of false conditional blocks:
The .fclist directive allows the listing of false conditional blocks (conditional blocks that do not produce code).
The .fcnolist directive suppresses the listing of false conditional blocks until a .fclist directive is encountered. With .fcnolist, only code in conditional blocks that are actually assembled appears in the listing. The .if, .elseif, .else, and .endif directives do not appear.
By default, all conditional blocks are listed; the assembler acts as if the .fclist directive had been used.
This example shows the assembly language and listing files for code with and without the conditional blocks listed.
Source file:
a .set 0
b .set 1
.fclist ; list false conditional blocks
.if a
MVK 5,A0
.else
MVK 0,A0
.endif
.fcnolist ; do not list false conditional blocks
.if a
MVK 5,A0
.else
MVK 0,A0
.endif
Listing file:
1 00000000 a .set 0
2 00000001 b .set 1
3 .fclist ; list false conditional blocks
4 .if a
5 MVK 5,A0
6 .else
7 00000000 00000028 MVK 0,A0
8 .endif
9 .fcnolist ; do not list false conditional blocks
13 00000004 00000028 MVK 0,A0
.fieldvalue[, size in bits]
The .field directive initializes a multiple-bit field within a single word (32 bits) of memory. This directive has two operands:
"t.asm", WARNING! at line 1: [W0001] Value truncated to 1
.field 3, 1
Successive .field directives pack values into the specified number of bits starting at the current 32-bit location. Fields are packed starting at the least significant bit (bit 0), moving toward the most significant bit (bit 31) as more fields are added. If the assembler encounters a field size that does not fit in the current 32-bit word, it fills the remaining bits of the current byte with 0s, increments the SPC to the next word boundary, and begins packing fields into the next word.
The .field directive is similar to the .bits directive (see the .bits topic). However, the .bits directive does not allow you to specify the number of bits in the field and does not automatically increment the SPC when a word boundary is reached.
Use the .align directive to force the next .field directive to begin packing a new word.
If you use a label, it points to the byte that contains the specified field.
When you use .field in a .struct/.endstruct sequence, .field defines a member's size; it does not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
This example shows how fields are packed into a word. The SPC does not change until a word is filled and the next word is begun.
1 ************************************
2 ** Initialize a 24-bit field. **
3 ************************************
4 00000000 00BBCCDD .field 0BBCCDDh, 24
5
6 ************************************
7 ** Initialize a 5-bit field **
8 ************************************
9 00000000 0ABBCCDD .field 0Ah, 5
10
11 ***********************************
12 ** Initialize a 4-bit field **
13 ** in a new word. **
14 ************************************
15 00000004 0000000C .field 0Ch, 4
16
17 ************************************
18 ** Initialize a 3-bit field **
19 ************************************
20 00000004 0000001C x: .field 01h, 3
21
22 ************************************
23 ** Initialize a 32-bit field **
24 ** relocatable field in the **
25 ** next word **
26 ************************************
27 00000008 00000004' .field x
Figure 5-6 shows how the directives in this example affect memory.
.floatvalue[, ... ,valuen]
The .float directive places the IEEE single-precision floating-point representation of a single floating-point constant into a word in the current section. The value must be an absolute constant expression with an arithmetic type or a symbol equated to an absolute constant expression with an arithmetic type. Each constant is converted to a floating-point value in IEEE single-precision 32-bit format.
With big-endian ordering, the 32-bit value is stored exponent byte first, most significant byte of fraction second, and least significant byte of fraction third, in the format shown in Figure 5-7.
When you use .float in a .struct/.endstruct sequence, .float defines a member's size; it does not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
Following are examples of the .float directive:
1 00000000 E9045951 .float -1.0e25
2 00000004 40400000 .float 3
3 00000008 42F60000 .float 123
.global symbol1[, ... ,symboln]
.def symbol1[, ... ,symboln]
.ref symbol1[, ... ,symboln]
Three directives identify global symbols that are defined externally or can be referenced externally:
The .def directive identifies a symbol that is defined in the current module and can be accessed by other files. The assembler places this symbol in the symbol table.
The .ref directive identifies a symbol that is used in the current module but is defined in another module. The linker resolves this symbol's definition at link time.
The .global directive acts as a .ref or a .def, as needed.
A global symbol is defined in the same manner as any other symbol; that is, it appears as a label or is defined by the .set, .equ, .bss, or .usect directive. If a global symbol is defined more than once, the linker issues a multiple-definition error. (The assembler can provide a similar multiple-definition error for local symbols.) The .ref directive always creates a symbol table entry for a symbol, whether the module uses the symbol or not; .global, however, creates an entry only if the module actually uses the symbol.
A symbol can be declared global for either of two reasons:
This example shows four files. The file1.lst and file2.lst refer to each other for all symbols used; file3.lst and file4.lst are similarly related.
The file1.lst and file3.lst files are equivalent. Both files define the symbol INIT and make it available to other modules; both files use the external symbols X, Y, and Z. Also, file1.lst uses the .global directive to identify these global symbols; file3.lst uses .ref and .def to identify the symbols.
The file2.lst and file4.lst files are equivalent. Both files define the symbols X, Y, and Z and make them available to other modules; both files use the external symbol INIT. Also, file2.lst uses the .global directive to identify these global symbols; file4.lst uses .ref and .def to identify the symbols.
file1.lst
1 ; Global symbol defined in this file
2 .global INIT
3 ; Global symbols defined in file2.lst
4 .global X, Y, Z
5 00000000 INIT:
6 00000000 00902058 ADD.L1 0x01,A4,A1
7 00000004 00000000! .word X
8 ; .
9 ; .
10 ; .
11 .end
file2.lst
1 ; Global symbols defined in this file
2 .global X, Y, Z
3 ; Global symbol defined in file1.lst
4 .global INIT
5 00000001 X: .set 1
6 00000002 Y: .set 2
7 00000003 Z: .set 3
8 00000000 00000000! .word INIT
9 ; .
10 ; .
11 ; .
12 .end
file3.lst
1 ; Global symbol defined in this file
2 .def INIT
3 ; Global symbols defined in file4.lst
4 .ref X, Y, Z
5 00000000 INIT:
6 00000000 00902058 ADD.L1 0x01,A4,A1
7 00000004 00000000! .word X
8 ; .
9 ; .
10 ; .
11 .end
file4.lst
1 ; Global symbols defined in this file
2 .def X, Y, Z
3 ; Global symbol defined in file3.lst
4 .ref INIT
5 00000001 X: .set 1
6 00000002 Y: .set 2
7 00000003 Z: .set 3
8 00000000 00000000! .word INIT
9 ; .
10 ; .
11 ; .
12 .end
.group group section name group type
.gmember section name
.endgroup
Three directives instruct the assembler to make certain sections members of an ELF group section (see the ELF specification for more information on group sections).
The .group directive begins the group declaration. The group section name designates the name of the group section. The group type designates the type of the group. The following types are supported:
0x0 | Regular ELF group | |
0x1 | COMDAT ELF group |
Duplicate COMDAT (common data) groups are allowed in multiple modules; the linker keeps only one. Creating such duplicate groups is useful for late instantiation of C++ templates and for providing debugging information.
The .gmember directive designates section name as a member of the group.
The .endgroup directive ends the group declaration.
.half value1[, ... ,valuen]
.short value1[, ... ,valuen]
.uhalf value1[, ... ,valuen]
.ushort value1[, ... ,valuen]
The .half, .uhalf, .short, and .ushort directives place one or more values into consecutive halfwords in the current section. Each value is placed in a 2-byte memory location by itself. A value can be either:
The assembler truncates values greater than 16 bits.
If you use a label with .half, .short, .uhalf, or .ushort; it points to the location where the assembler places the first byte.
These directives perform a halfword (16-bit) alignment before data is written to the section. This guarantees that data resides on a 16-bit boundary.
When you use .half, .short, .uhalf, or .ushort in a .struct/.endstruct sequence, they define a member's size; they do not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
In this example, .half is used to place 16-bit values (10, -1, abc, and a) into consecutive halfwords in memory; .short is used to place 16-bit values (8, -3, def, and b) into consecutive halfwords in memory. The label STRN has the value 100ch, which is the location of the first initialized halfword for .short.
1 00000000 .space 100h * 16
2 00001000 0000000A .half 10, -1, "abc", 'a'
00001002 0000FFFF
00001004 00000061
00001006 00000062
00001008 00000063
0000100a 00000061
3 0000100c 00000008 STRN .short 8, -3, "def", 'b'
0000100e 0000FFFD
00001010 00000064
00001012 00000065
00001014 00000066
00001016 00000062
.ifcondition
[.elseifcondition]
[.else]
.endif
These directives provide conditional assembly:
The .if directive marks the beginning of a conditional block. The condition is a required parameter.
The .elseif directive identifies a block of code to be assembled when the .if expression is false (0) and the .elseif expression is true (nonzero). When the .elseif expression is false, the assembler continues to the next .elseif (if present), .else (if present), or .endif (if no .elseif or .else is present). The .elseif is optional in a conditional block, and more than one .elseif can be used. If an expression is false and there is no .elseif, the assembler continues with the code that follows a .else (if present) or a .endif.
The .else directive identifies a block of code that the assembler assembles when the .if expression and all .elseif expressions are false (0). The .else directive is optional in the conditional block; if an expression is false and there is no .else statement, the assembler continues with the code that follows the .endif. The .elseif and .else directives can be used in the same conditional assembly block.
The .endif directive terminates a conditional block.
See Section 4.9.2 for information about relational operators.
This example shows conditional assembly:
1 00000001 SYM1 .set 1
2 00000002 SYM2 .set 2
3 00000003 SYM3 .set 3
4 00000004 SYM4 .set 4
5
6 If_4: .if SYM4 = SYM2 * SYM2
7 00000000 00000004 .byte SYM4 ; Equal values
8 .else
9 .byte SYM2 * SYM2 ; Unequal values
10 .endif
11
12 If_5: .if SYM1 <;= 10
13 00000001 0000000A .byte 10 ; Less than / equal
14 .else
15 .byte SYM1 ; Greater than
16 .endif
17
18 If_6: .if SYM3 * SYM2 != SYM4 + SYM2
19 .byte SYM3 * SYM2 ; Unequal value
20 .else
21 00000002 00000008 .byte SYM4 + SYM4 ; Equal values
22 .endif
23
24 If_7: .if SYM1 = SYM2
25 .byte SYM1
26 .elseif SYM2 + SYM3 = 5
27 00000003 00000005 .byte SYM2 + SYM3
28 .endif
.import "symbolname"
.export "symbolname"
.hidden "symbolname"
.protected "symbolname"
These directives set the dynamic visibility of a global symbol. Each takes a single symbol name, optionally enclosed in double-quotes.
See Section 8.12 for an explanation of symbol visibility.
Theses directives are commonly used in the context of dynamic linking. For more about dynamic linking, see Chapter 14 of The C6000 Embedded Application Binary Interface Application Report (SPRAB89).
.intvalue1[, ... ,valuen]
.uintvalue1[, ... ,valuen]
.longvalue1[, ... ,valuen]
.ulongvalue1[, ... ,valuen]
.wordvalue1[, ... ,valuen]
.uwordvalue1[, ... ,valuen]
The .int, .unint, .long, .ulong, .word, and .uword directives place one or more values into consecutive words in the current section. Each value is placed in a 32-bit word by itself and is aligned on a word boundary. A value can be either:
A value can be either an absolute or a relocatable expression. If an expression is relocatable, the assembler generates a relocation entry that refers to the appropriate symbol; the linker can then correctly patch (relocate) the reference. This allows you to initialize memory with pointers to variables or labels.
If you use a label with these directives, it points to the first word that is initialized.
When you use these directives in a .struct/.endstruct sequence, they define a member's size; they do not initialize memory. See the .struct/.endstruct/.tag topic.
This example uses the .int directive to initialize words. Notice that the symbol SYMPTR puts the symbol's address in the object code and generates a relocatable reference (indicated by the - character appended to the object word).
1 00000000 .space 73h
2 00000000 .bss PAGE, 128
3 00000080 .bss SYMPTR, 3
4 00000074 003C12E4 INST: LDW.D2 *++B15[0],A0
5 00000078 0000000A .int 10, SYMPTR, -1, 35 + 'a', INST
0000007c 00000080-
00000080 FFFFFFFF
00000084 00000084
00000088 00000074'
This example initializes two 32-bit fields and defines DAT1 to point to the first location. The contents of the resulting 32-bit fields are FFFABCDh and 141h.
1 00000000 FFFFABCD DAT1: .long 0FFFFABCDh,'A'+100h
00000004 00000141
This example initializes five words. The symbol WordX points to the first word.
1 00000000 00000C80 ;WordX .word 3200,1+'AB',-'AF',0F410h,'A'
00000004 00004242
00000008 FFFFB9BF
0000000c 0000F410
00000010 00000041
.labelsymbol
The .label directive defines a special symbol that refers to the load-time address rather than the run-time address within the current section. Most sections created by the assembler have relocatable addresses. The assembler assembles each section as if it started at 0, and the linker relocates it to the address at which it loads and runs.
For some applications, it is desirable to have a section load at one address and run at a different address. For example, you may want to load a block of performance-critical code into slower memory to save space and then move the code to high-speed memory to run it. Such a section is assigned two addresses at link time: a load address and a run address. All labels defined in the section are relocated to refer to the run-time address so that references to the section (such as branches) are correct when the code runs. See Section 3.5 for more information about run-time relocation.
The .label directive creates a special label that refers to the load-time address. This function is useful primarily to designate where the section was loaded for purposes of the code that relocates the section.
This example shows the use of a load-time address label.
sect ".examp"
.label examp_load ; load address of section
start: ; run address of section
<code>
finish: ; run address of section end
.label examp_end ; load address of section end
See Section 8.5.6 for more information about assigning run-time and load-time addresses in the linker.
.length [page length]
.width [page width]
Two directives allow you to control the size of the output listing file.
The .length directive sets the page length of the output listing file. It affects the current and following pages. You can reset the page length with another .length directive.
The .width directive sets the page width of the output listing file. It affects the next line assembled and the lines following. You can reset the page width with another .width directive.
The width refers to a full line in a listing file; the line counter value, SPC value, and object code are counted as part of the width of a line. Comments and other portions of a source statement that extend beyond the page width are truncated in the listing.
The assembler does not list the .width and .length directives.
The following example shows how to change the page length and width.
********************************************
** Page length = 65 lines **
** Page width = 85 characters **
********************************************
.length 65
.width 85
********************************************
** Page length = 55 lines **
** Page width = 100 characters **
********************************************
.length 55
.width 100
.list
.nolist
Two directives enable you to control the printing of the source listing:
The .list directive allows the printing of the source listing.
The .nolist directive suppresses the source listing output until a .list directive is encountered. The .nolist directive can be used to reduce assembly time and the source listing size. It can be used in macro definitions to suppress the listing of the macro expansion.
The assembler does not print the .list or .nolist directives or the source statements that appear after a .nolist directive. However, it continues to increment the line counter. You can nest the .list/.nolist directives; each .nolist needs a matching .list to restore the listing.
By default, the source listing is printed to the listing file; the assembler acts as if the .list directive had been used. However, if you do not request a listing file when you invoke the assembler by including the --asm_listing option on the command line (see Section 4.3), the assembler ignores the .list directive.
This example shows how the .list and .nolist directives turn the output listing on and off. The .nolist, the table: .data through .byte lines, and the .list directives do not appear in the listing file. Also, the line counter is incremented even when source statements are not listed.
Source file:
.data
.space 0CCh
.text
ABS A0,A1
.nolist
table: .data
.word -1
.byte 0FFh
.list
.text
MV A0,A1
.data
coeff .word 00h,0ah,0bh
Listing file:
1 00000000 .data
2 00000000 .space 0CCh
3 00000000 .text
4 00000000 00800358 ABS A0,A1
5
13
14 00000004 .text
15 00000004 008001A0 MV A0,A1
16 000000d1 .data
17 000000d4 00000000 coeff .word 00h,0ah,0bh
000000d8 0000000A
000000dc 0000000B
.loop [count]
.break [end-condition]
.endloop
Three directives allow you to repeatedly assemble a block of code:
The .loop directive begins a repeatable block of code. The optional count operand, if used, must be a well-defined integer expression. The count indicates the number of loops to be performed (the loop count). If count is omitted, it defaults to 1024. The loop will be repeated count number of times, unless terminated early by a .break directive.
The optional .break directive terminates a .loop early. You may use .loop without using .break. The .break directive terminates a .loop only if the end-condition expression is true (evaluates to nonzero). If the optional end-condition operand is omitted, it defaults to true. If end-condition is true, the assembler stops repeating the .loop body immediately; any remaining statements after .break and before .endloop are not assembled. The assembler resumes assembling with the statement after the .endloop directive. If end-condition is false (evaluates to 0), the loop continues.
The .endloop directive marks the end of a repeatable block of code. When the loop terminates, whether by a .break directive with a true end-condition or by performing the loop count number of iterations, the assembler stops repeating the loop body and resumes assembling with the statement after the .endloop directive.
This example illustrates how these directives can be used with the .eval directive. The code in the first six lines expands to the code immediately following those six lines.
1 .eval 0,x
2 COEF .loop
3 .word x*100
4 .eval x+1, x
5 .break x = 6
6 .endloop
1 00000000 00000000 .word 0*100
1 .eval 0+1, x
1 .break 1 = 6
1 00000004 00000064 .word 1*100
1 .eval 1+1, x
1 .break 2 = 6
1 00000008 000000C8 .word 2*100
1 .eval 2+1, x
1 .break 3 = 6
1 0000000c 0000012C .word 3*100
1 .eval 3+1, x
1 .break 4 = 6
1 00000010 00000190 .word 4*100
1 .eval 4+1, x
1 .break 5 = 6
1 00000014 000001F4 .word 5*100
1 .eval 5+1, x
1 .break 6 = 6
macname .macro [parameter1[, ... ,parametern]]
model statements or macro directives
.endm
The .macro and .endm directives are used to define 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, in an .include/.copy file, or in a macro library.
macname | names the macro. You must place the name in the source statement's label field. | |
.macro | identifies the source statement as the first line of a macro definition. You must place .macro in the opcode field. | |
[parameters] | are optional substitution symbols that appear as operands for the .macro directive. | |
model statements | are instructions or assembler directives that are executed each time the macro is called. | |
macro directives | are used to control macro expansion. | |
.endm | marks the end of the macro definition. |
Macros are explained in further detail in Section 6.
.map symbol1/register1[, symbol2/register2, ...]
.clearmap
The .map directive is used by the compiler when the input is linear assembly. The compiler tries to keep your symbolic names for registers defined with .reg by creating substitution symbols with .map.
The .map directive is similar to .asg, but uses a forward slash instead of a comma; and allows single quote characters in the symbolic names. For example, this linear assembly input:
The .clearmap directive is used by the compiler to undefine all current .map substitution symbols.
See the TMS320C6000 Optimizing Compiler User's Guide for details on using the .map directive in linear assembly code.
The .map directive is similar to .asg, but uses a forward slash instead of a comma; and allows single quote characters in the symbolic names. For example, this linear assembly input:
fn: .cproc a, b, c
.reg x, y, z
ADD a, b, z
ADD z, c, z
.return z
.endproc
Becomes this assembly code output:
fn:
.map a/A4
.map b/B4
.map c/A6
.map z/A4
.map z'/A3
RET .S2 B3
ADD .L1X a,b,z'
ADD .L1 z',c,z
NOP 3
.mlib"filename"
The .mlib directive provides the assembler with the filename of a macro library. A macro library is a collection of files that contain macro definitions. The macro definition files are bound into a single file (called a library or archive) by the archiver.
Each file in a macro library contains one macro definition that corresponds to the name of the file. The filename of a macro library member must be the same as the macro name, and its extension must be .asm. The filename must follow host operating system conventions; it can be enclosed in double quotes. You can specify a full pathname (for example, c:\320tools\macs.lib). If you do not specify a full pathname, the assembler searches for the file in the following locations in the order given:
See Section 4.5 for more information about the --include_path option.
A .mlib directive causes the assembler to open the library specified by filename and create a table of the library's contents. The assembler stores names of individual library members in the opcode table as library entries. This redefines any existing opcodes or macros with the same name. If one of these macros is called, the assembler extracts the library entry and loads it into the macro table. The assembler expands the library entry as it does other macros, but it does not place the source code in the listing. Only macros called from the library are extracted, and they are extracted only once.
See Section 6 for more information on macros and macro libraries.
The code creates a macro library that defines two macros, inc1.asm and dec1.asm. The file inc1.asm contains the definition of inc1 and dec1.asm contains the definition of dec1.
inc1.asm | dec1.asm |
---|---|
* Macro for incrementing
|
* Macro for decrementing
|
Use the archiver to create a macro library:
ar6x -a mac inc1.asm dec1.asm
Now you can use the .mlib directive to reference the macro library and define the inc1.asm and dec1.asm macros:
1 .mlib "mac.lib"
2
3 * Macro Call
4 00000000 inc1 A0
1 00000000 000021A0 ADD A0,1,A0
5
6 * Macro Call
7 00000004 dec1 B0
1 00000004 0003E1A2 SUB B0,1,B0
.mlist
.mnolist
Two directives enable you to control the listing of macro and repeatable block expansions in the listing file:
The .mlist directive allows macro and .loop/.endloop block expansions in the listing file.
The .mnolist directive suppresses macro and .loop/.endloop block expansions in the listing file.
By default, the assembler behaves as if the .mlist directive had been specified.
See Section 6 for more information on macros and macro libraries. See the .loop/.break/.endloop topic for information on conditional blocks.
This example defines a macro named STR_3. The first time the macro is called, the macro expansion is listed (by default). The second time the macro is called, the macro expansion is not listed, because a .mnolist directive was assembled. The third time the macro is called, the macro expansion is again listed because a .mlist directive was assembled.
1 STR_3 .macro P1, P2, P3
2 .string ":p1:", ":p2:", ":p3:"
3 .endm
4
5 00000000 STR_3 "as", "I", "am"
1 00000000 0000003A .string ":p1:", ":p2:", ":p3:"
00000001 00000070
00000002 00000031
00000003 0000003A
00000004 0000003A
00000005 00000070
00000006 00000032
00000007 0000003A
00000008 0000003A
00000009 00000070
0000000a 00000033
0000000b 0000003A
6 .mnolist
7 0000000c STR_3 "as", "I", "am"
8 .mlist
9 00000018 STR_3 "as", "I", "am"
1 00000018 0000003A .string ":p1:", ":p2:", ":p3:"
00000019 00000070
0000001a 00000031
0000001b 0000003A
0000001c 0000003A
0000001d 00000070
0000001e 00000032
0000001f 0000003A
00000020 0000003A
00000021 00000070
00000022 00000033
00000023 0000003A
.newblock
The .newblock directive undefines any local labels currently defined. Local labels, by nature, are temporary; the .newblock directive resets them and terminates their scope.
A local label is a label in the form $n, where n is a single decimal digit, or name?, where name is a legal symbol name. Unlike other labels, local labels are intended to be used locally, and cannot be used in expressions. They can be used only as operands in 8-bit jump instructions. Local labels are not included in the symbol table.
After a local label has been defined and (perhaps) used, you should use the .newblock directive to reset it. The .text, .data, and .sect directives also reset local labels. Local labels that are defined within an include file are not valid outside of the include file.
See Section 4.8.3 for more information on the use of local labels.
This example shows how the local label $1 is declared, reset, and then declared again.
1 .global table1, table2
2
3 00000000 00000028! MVKL table1,A0
4 00000004 00000068! MVKH table1,A0
5 00000008 008031A9 MVK 99, A1
6 0000000c 010848C0 || ZERO A2
7
8 00000010 80000212 $1:[A1] B $1
9 00000014 01003674 STW A2, *A0++
10 00000018 0087E1A0 SUB A1,1,A1
11 0000001c 00004000 NOP 3
12
13 .newblock ; undefine $1
14
15 00000020 00000028! MVKL table2,A0
16 00000024 00000068! MVKH table2,A0
17 00000028 008031A9 MVK 99, A1
18 0000002c 010829C0 || SUB A2,1,A2
19
20 00000030 80000212 $1:[A1] B $1
21 00000034 01003674 STW A2, *A0++
22 00000038 0087E1A0 SUB A1,1,A1
23 0000003c 00004000 NOP 3
.nocmp
The .nocmp directive instructs the compiler to not utilize 16-bit instructions for the code section .nocmp appears in. The .nocmp directive can appear anywhere in the section.
In the example, the section one is not compressed, whereas section two is compressed.
.sect "one"
LDW *A4, A5
LDW *B4, A5
.nocmp
NOP 4
ADD A4, A5, A6
ADD B4, B5, B6
NOP
...
.sect "two"
ADD A4, A5, A6
NOP
NOP
...
.noremarknum
.remark [num]
The .noremark directive suppresses the assembler remark identified by num. A remark is an informational assembler message that is less severe than a warning.
This directive is equivalent to using the -ar[num] assembler option.
The .remark directive re-enables the remark(s) previously suppressed.
This example uses .noremark to turn off remark #5001 and then .remark to turn it back on again.
Partial source file:
SPLOOP 1
SPMASK
|| CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
SPKERNEL 1,0
|| DADDSP .S2 B27:B26,B7:B6,B27:B26
NOP 5
.noremark 5001
SPLOOP 1
SPMASK
|| CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
SPKERNEL 1,0
|| DADDSP .S2 B27:B26,B7:B6,B27:B26
NOP 5
.remark 5001
SPLOOP 1
SPMASK
|| CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
SPKERNEL 1,0
|| DADDSP .S2 B27:B26,B7:B6,B27:B26
NOP 5
Resulting listing file:
1
2 ; Example using .noremark to turn off remark #5001 and
3 ; then .remark to turn it back on again
4
5 00000000 0c66 SPLOOP 1
6
7 00000002 2c66 SPMASK
8 00000004 12490f02 || CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
9
10 00000008 08034001 SPKERNEL 1,0
11 0000000c 1d1b4b22 || DADDSP .S2 B27:B26,B7:B6,B27:B26
12
13 00000010 8c6e NOP 5
14
15 .noremark 5001
16
17 00000012 0c66 SPLOOP 1
18
19 00000014 00030001 SPMASK
20 00000018 12490f02 || CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
21
22 00000020 08034001 SPKERNEL 1,0
23 00000024 1d1b4b22 || DADDSP .S2 B27:B26,B7:B6,B27:B26
24
25 00000028 8c6e NOP 5
26
27 .remark 5001
28
29 0000002a 0c66 SPLOOP 1
"sploopex.asm", REMARK at line 29: [R5001] SDSCM00012367 potentially triggered by this
execute packet sequence. SPLOOP must be
30
31 0000002c 00030001 SPMASK
32 00000030 12490f02 || CMPYSP .M2 B9:B8,B19:B18,B7:B6:B5:B4
33
34 00000034 08034001 SPKERNEL 1,0
35 00000038 1d1b4b22 || DADDSP .S2 B27:B26,B7:B6,B27:B26
36
37 00000040 00008000 NOP 5
.optionoption1[, option2,. . .]
The .option directive selects options for the assembler output listing. The options must be separated by commas; each option selects a listing feature. These are valid options:
A | turns on listing of all directives and data, and subsequent expansions, macros, and blocks. | |
B | limits the listing of .byte and .char directives to one line. | |
D | turns off the listing of certain directives (same effect as .drnolist). | |
H | limits the listing of .half and .short directives to one line. | |
L | limits the listing of .long directives to one line. | |
M | turns off macro expansions in the listing. | |
N | turns off listing (performs .nolist). | |
O | turns on listing (performs .list). | |
R | resets any B, H, L, M, T, and W (turns off the limits of B, H, L, M, T, and W). | |
T | limits the listing of .string directives to one line. | |
W | limits the listing of .word and .int directives to one line. | |
X | produces a cross-reference listing of symbols. You can also obtain a cross-reference listing by invoking the assembler with the --asm_listing_cross_reference option (see Section 4.3). |
Options are not case sensitive.
This example shows how to limit the listings of the .byte, .char, .int, long, .word, and .string directives to one line each.
1 ****************************************
2 ** Limit the listing of .byte, .char, **
3 ** .int, .word, and .string **
4 ** directives to 1 line each. **
5 ****************************************
6 .option B, W, T
7 00000000 000000BD .byte -'C', 0B0h, 5
8 00000003 000000BC .char -'D', 0C0h, 6
9 00000008 0000000A .int 10, 35 + 'a', "abc"
10 0000001c AABBCCDD .long 0AABBCCDDh, 536 + 'A'
11 00000024 000015AA .word 5546, 78h
12 0000002c 00000052 .string "Registers"
13
14 ****************************************
15 ** Reset the listing options. **
16 ****************************************
17 .option R
18 00000035 000000BD .byte -'C', 0B0h, 5
00000036 000000B0
00000037 00000005
19 00000038 000000BC .char -'D', 0C0h, 6
00000039 000000C0
0000003a 00000006
20 0000003c 0000000A .int 10, 35 + 'a', "abc"
00000040 00000084
00000044 00000061
00000048 00000062
0000004c 00000063
21 00000050 AABBCCDD .long 0AABBCCDDh, 536 + 'A'
00000054 00000259
22 00000058 000015AA .word 5546, 78h
0000005c 00000078
23 00000060 00000052 .string "Registers"
00000061 00000065
00000062 00000067
00000063 00000069
00000064 00000073
00000065 00000074
00000066 00000065
00000067 00000072
00000068 00000073
.page
The .page directive produces a page eject in the listing file. The .page directive is not printed in the source listing, but the assembler increments the line counter when it encounters the .page directive. Using the .page directive to divide the source listing into logical divisions improves program readability.
This example shows how the .page directive causes the assembler to begin a new page of the source listing.
Source file:
Source file (generic)
.title "**** Page Directive Example ****"
; .
; .
; .
.page
Listing file:
TMS320C6000 Assembler Version x.xx Day Time Year
Copyright (c) 1996-2011 Texas Instruments Incorporated
**** Page Directive Example **** PAGE 1
2 ; .
3 ; .
4 ; .
TMS320C6000 Assembler Version x.xx Day Time Year
Copyright (c) 1996-2011 Texas Instruments Incorporated
**** Page Directive Example **** PAGE 2
No Errors, No Warnings
.retain["section name"]
.retainrefs["section name"]
The .retain directive indicates that the current or specified section is not eligible for removal via conditional linking. You can also override conditional linking for a given section with the --retain linker option. You can disable conditional linking entirely with the --unused_section_elimination=off linker option.
The .retainrefs directive indicates that any sections that refer to the current or specified section are not eligible for removal via conditional linking. For example, applications may use an .intvecs section to set up interrupt vectors. The .intvecs section is eligible for removal during conditional linking by default. You can force the .intvecs section and any sections that reference it to be retained by applying the .retain and .retainrefs directives to the .intvecs section.
The section name identifies the section. If the directive is used without a section name, it applies to the current initialized section. If the directive is applied to an uninitialized section, the section name is required. The section name must be enclosed in double quotes. A section name can contain a subsection name in the form section name:subsection name.
The linker assumes that all sections by default are eligible for removal via conditional linking. (However, the linker does automatically retain the .reset section.) The .retain directive is useful for overriding this default conditional linking behavior for sections that you want to keep included in the link, even if the section is not referenced by any other section in the link. For example, you could apply a .retain directive to an interrupt function that you have written in assembly language, but which is not referenced from any normal entry point in the application.
This example of an interrupt function that has a .retain directive applied to it.
.sect ".text:interrupts:retain"
.retain
.global _int_func1
;******************************************************************************
;* FUNCTION NAME: int_func1 *
;******************************************************************************
_int_func1:
STW .D2 FP,*SP++(-88) ; [B_D] |31|
STW .D2 B3,*SP(80) ; [B_D] |31|
STW .D2 A4,*SP(24) ; [B_D] |31|
STW .D2 B2,*SP(84) ; [B_D] |31|
STW .D2 B9,*SP(76) ; [B_D] |31|
STW .D2 B8,*SP(72) ; [B_D] |31|
STW .D2 B7,*SP(68) ; [B_D] |31|
STW .D2 B6,*SP(64) ; [B_D] |31|
STW .D2 B5,*SP(60) ; [B_D] |31|
STW .D2 B4,*SP(56) ; [B_D] |31|
STW .D2 B1,*SP(52) ; [B_D] |31|
STW .D2 B0,*SP(48) ; [B_D] |31|
STW .D2 A7,*SP(36) ; [B_D] |31|
STW .D2 A6,*SP(32) ; [B_D] |31|
STW .D2 A5,*SP(28) ; [B_D] |31|
CALL .S1 _foo ; [A_S] |32|
|| STW .D2 A8,*SP(40) ; [B_D] |31|
...
STW .D2 B4,*+DP(_a_i) ; [B_D] |33|
RET .S2 IRP ; [B_Sb] |34|
|| LDW .D2 *SP(56),B4 ; [B_D] |34|
LDW .D2 *++SP(88),FP ; [B_D] |34|
NOP 4 ; [A_L]
.sect "section name"
.sect "section name" [,{RO|RW}] [,{ALLOC|NOALLOC}]
The .sect directive defines a named section that can be used like the default .text and .data sections. The .sect directive sets section name to be the current section; the lines that follow are assembled into the section name section.
The section name identifies the section. The section name must be enclosed in double quotes. A section name can contain a subsection name in the form section name:subsection name. See Section 2 for more information about sections.
The sections can be marked read-only (RO) or read-write (RW). Also, the sections can be marked for allocation (ALLOC) or no allocation (NOALLOC). These attributes can be specified in any order, but only one attribute from each set can be selected. RO conflicts with RW, and ALLOC conflicts with NOALLOC. If conflicting attributes are specified the assembler generates an error, for example:
"t.asm", ERROR! at line 1:[E0000] Attribute RO cannot be combined with attr RW
.sect "illegal_sect",RO,RW
This example defines two special-purpose sections, Sym_Defs and Vars, and assembles code into them.
1 **********************************************
2 ** Begin assembling into .text section. **
3 **********************************************
4 00000000 .text
5 00000000 000005E0 ZERO A0
6 00000004 008425E0 ZERO A1
7
8 **********************************************
9 ** Begin assembling into vars section. **
10 **********************************************
11 00000000 .sect "vars"
12 00000000 4048F5C3 pi .float 3.14
13 00000004 000007D0 max .int 2000
14 00000008 00000001 min .int 1
15
16 **********************************************
17 ** Resume assembling into .text section. **
18 **********************************************
19 00000008 .text
20 00000008 010000A8 MVK 1,A2
21 0000000c 018000A8 MVK 1,A3
22
23 **********************************************
24 ** Resume assembling into vars section. **
25 **********************************************
26 0000000c .sect "vars"
27 0000000c 00000019 count .short 25
symbol .set value
symbol .equ value
The .setand .equ directives equate a constant value to a .set/.equ symbol. The symbol can then be used in place of a value in assembly source. This allows you to equate meaningful names with constants and other values. The .set and .equ directives are identical and can be used interchangeably.
Undefined external symbols and symbols that are defined later in the module cannot be used in the expression. If the expression is relocatable, the symbol to which it is assigned is also relocatable.
The value of the expression appears in the object field of the listing. This value is not part of the actual object code and is not written to the output file.
Symbols defined with .set or .equ can be made externally visible with the .def or .global directive (see the .global/.def/.ref topic). In this way, you can define global absolute constants.
This example shows how symbols can be assigned with .set and .equ.
1 **********************************************
2 ** Equate symbol AUX_R1 to register A1 **
3 ** and use it instead of the register. **
4 **********************************************
5 00000001 AUX_R1 .set A1
6 00000000 00B802D4 STH AUX_R1,*+B14
7
8 **********************************************
9 ** Set symbol index to an integer expr. **
10 ** and use it as an immediate operand. **
11 **********************************************
12 00000035 INDEX .equ 100/2 +3
13 00000004 01001AD0 ADDK INDEX, A2
14
15 **********************************************
16 ** Set symbol SYMTAB to a relocatable expr. **
17 ** and use it as a relocatable operand. **
18 **********************************************
19 00000008 0000000A LABEL .word 10
20 00000009' SYMTAB .set LABEL + 1
21
22 **********************************************
23 ** Set symbol NSYMS equal to the symbol **
24 ** INDEX and use it as you would INDEX. **
25 **********************************************
26 00000035 NSYMS .set INDEX
27 0000000c 00000035 .word NSYMS
[label] .space size in bytes
[label] .bes size in bytes
The .spaceand .bes directives reserve the number of bytes given by size in bytes in the current section and fill them with 0s. The section program counter is incremented to point to the word following the reserved space.
When you use a label with the .space directive, it points to the first byte reserved. When you use a label with the .bes directive, it points to the last byte reserved.
This example shows how memory is reserved with the .space and .bes directives.
1 *****************************************************
2 ** Begin assembling into the .text section. **
3 *****************************************************
4 00000000 .text
5 *****************************************************
6 ** Reserve 0F0 bytes (60 words in .text section). **
7 *****************************************************
8 00000000 .space 0F0h
9 000000f0 00000100 .word 100h, 200h
000000f4 00000200
10 *****************************************************
11 ** Begin assembling into the .data section. **
12 *****************************************************
13 00000000 .data
14 00000000 00000049 .string "In .data"
00000001 0000006E
00000002 00000020
00000003 0000002E
00000004 00000064
00000005 00000061
00000006 00000074
00000007 00000061
15 *****************************************************
16 ** Reserve 100 bytes in the .data section; **
17 ** RES_1 points to the first word **
18 ** that contains reserved bytes. **
19 *****************************************************
20 00000008 RES_1: .space 100
21 0000006c 0000000F .word 15
22 00000070 00000008" .word RES_1
23 *****************************************************
24 ** Reserve 20 bytes in the .data section; **
25 ** RES_2 points to the last word **
26 ** that contains reserved bytes. **
27 *****************************************************
28 00000087 RES_2: .bes 20
29 00000088 00000036 .word 36h
30 0000008c 00000087" .word RES_2
.sslist
.ssnolist
Two directives allow you to control substitution symbol expansion in the listing file:
The .sslist directive allows substitution symbol expansion in the listing file. The expanded line appears below the actual source line.
The .ssnolist directive suppresses substitution symbol expansion in the listing file.
By default, all substitution symbol expansion in the listing file is suppressed; the assembler acts as if the .ssnolist directive had been used.
Lines with the pound (#) character denote expanded substitution symbols.
This example shows code that, by default, suppresses the listing of substitution symbol expansion, and it shows the .sslist directive assembled, instructing the assembler to list substitution symbol code expansion.
1 00000000 .bss x,4
2 00000004 .bss y,4
3 00000008 .bss z,4
4
5 addm .macro src1,src2,dst
6 LDW *+B14(:src1:), A0
7 LDW *+B14(:src2:), A1
8 NOP 4
9 ADD A0,A1,A0
10 STW A0,*+B14(:dst:)
11 .endm
12
13 00000000 addm x,y,z
1 00000000 0000006C- LDW *+B14(x), A0
1 00000004 0080016C- LDW *+B14(y), A1
1 00000008 00006000 NOP 4
1 0000000c 000401E0 ADD A0,A1,A0
1 00000010 0000027C- STW A0,*+B14(z)
14
15 .sslist
16 00000014 addm x,y,z
1 00000014 0000006C- LDW *+B14(:src1:), A0
# LDW *+B14(x), A0
1 00000018 0080016C- LDW *+B14(:src2:), A1
# LDW *+B14(y), A1
1 0000001c 00006000 NOP 4
1 00000020 000401E0 ADD A0,A1,A0
1 00000024 0000027C- STW A0,*+B14(:dst:)
# STW A0,*+B14(z)
17
.string {expr1 | "string1"} [, ... , {exprn | "stringn"} ]
.cstring {expr1 | "string1"} [, ... , {exprn | "stringn"} ]
The .string and .cstring directives place 8-bit characters from a character string into the current section. The expr or string can be one of the following:
The .cstring directive adds a NUL character needed by C; the .string directive does not add a NUL character. In addition, .cstring interprets C escapes (\\ \a \b \f \n \r \t \v \<octal>).
The assembler truncates any values that are greater than eight bits. Operands must fit on a single source statement line.
If you use a label, it points to the location of the first byte that is initialized.
When you use .string and .cstring in a .struct/.endstruct sequence, the directive only defines a member's size; it does not initialize memory. For more information, see the .struct/.endstruct/.tag topic.
In this example, 8-bit values are placed into consecutive bytes in the current section. The label Str_Ptr has the value 0h, which is the location of the first initialized byte.
1 00000000 00000041 Str_Ptr: .string "ABCD"
00000001 00000042
00000002 00000043
00000003 00000044
2 00000004 00000041 .string 41h, 42h, 43h, 44h
00000005 00000042
00000006 00000043
00000007 00000044
3 00000008 00000041 .string "Austin", "Houston"
00000009 00000075
0000000a 00000073
0000000b 00000074
0000000c 00000069
0000000d 0000006E
0000000e 00000048
0000000f 0000006F
00000010 00000075
00000011 00000073
00000012 00000074
00000013 0000006F
00000014 0000006E
4 00000015 00000030 .string 36 + 12
[stag] .struct [expr]
[mem0] element [expr0]
[mem1] element [expr1]
. . .
. . .
. . .
[memn] .tag stag [exprn]
. . .
. . .
. . .
[memN] element [exprN]
[size] .endstruct
label .tag stag
The .struct directive assigns symbolic offsets to the elements of a data structure definition. This allows you to group similar data elements together and let the assembler calculate the element offset. This is similar to a C structure or a Pascal record. The .struct directive does not allocate memory; it merely creates a symbolic template that can be used repeatedly.
The .endstruct directive terminates the structure definition.
The .tag directive gives structure characteristics to a label, simplifying the symbolic representation and providing the ability to define structures that contain other structures. The .tag directive does not allocate memory. The structure tag (stag) of a .tag directive must have been previously defined.
Following are descriptions of the parameters used with the .struct, .endstruct, and .tag directives:
NOTE
Directives that Can Appear in a .struct/.endstruct SequenceThe only directives that can appear in a .struct/.endstruct sequence are element descriptors, conditional assembly directives, and the .align directive, which aligns the member offsets on word boundaries. Empty structures are illegal.
The following examples show various uses of the .struct, .tag, and .endstruct directives.
1 real_rec .struct ; stag
2 00000000 nom .int ; member1 = 0
3 00000004 den .int ; member2 = 1
4 00000008 real_len .endstruct ; real_len = 2
5
6 00000000 0080016C- LDW *+B14(real+real_rec.den), A1
7 ; access structure
8
9 00000000 .bss real, real_len ; allocate mem rec
10
11 cplx_rec .struct ; stag
12 00000000 reali .tag real_rec ; member1 = 0
13 00000008 imagi .tag real_rec ; member2 = 2
14 00000010 cplx_len .endstruct ; cplx_len = 4
15
16 complex .tag cplx_rec ; assign structure
17 ; attribute
18 00000008 .bss complex, cplx_len ; allocate mem rec
19
20 00000004 0100046C- LDW *+B14(complex.imagi.nom), A2
21 ; access structure
22 00000008 0100036C- LDW *+B14(complex.reali.den), A2
23 ; access structure
24 0000000c 018C4A78 CMPEQ A2, A3, A3
1 .struct ; no stag puts
2 ; mems into global
3 ; symbol table
4
5 00000000 X .byte ; create 3 dim
6 00000001 Y .byte ; templates
7 00000002 Z .byte
8 00000003 .endstruct
1 bit_rec .struct ; stag
2 00000000 stream .string 64
3 00000040 bit7 .field 7 ; bit7 = 64
4 00000040 bit1 .field 9 ; bit9 = 64
5 00000042 bit5 .field 10 ; bit5 = 64
6 00000044 x_int .byte ; x_int = 68
7 00000045 bit_len .endstruct ; length = 72
8
9 bits .tag bit_rec
10 00000000 .bss bits, bit_len
11
12 00000000 0100106C- LDW *+B14(bits.bit7), A2
13 ; load field
14 00000004 0109E7A0 AND 0Fh, A2, A2 ; mask off garbage
.symdepend dst symbol name[,src symbol name]
.weak symbol name
These directives are used to affect symbol linkage and visibility.
The .symdepend directive creates an artificial reference from the section defining src symbol name to the symbol dst symbol name. This prevents the linker from removing the section containing dst symbol name if the section defining src symbol name is included in the output module. If src symbol name is not specified, a reference from the current section is created.
The .weak directive identifies a symbol that is used in the current module but is defined in another module. The linker resolves this symbol's definition at link time. Instead of including a weak symbol in the output file's symbol table by default (as it would for a global symbol), the linker only includes a weak symbol in the output of a "final" link if the symbol is required to resolve an otherwise unresolved reference. See Section 2.6.2 for details about how weak symbols are handled by the linker.
The .weak directive is equivalent to the .ref directive, except that the reference has weak linkage.
A global symbol is defined in the same manner as any other symbol; that is, it appears as a label or is defined by the .set, .equ, .bss, or .usect directive. If a global symbol is defined more than once, the linker issues a multiple-definition error. (The assembler can provide a similar multiple-definition error for local symbols.) The .weak directive always creates a symbol table entry for a symbol, whether the module uses the symbol or not; .symdepend, however, creates an entry only if the module actually uses the symbol.
A symbol can be declared global in either of the following ways:
For example, use the .weak and .set directives in combination as shown in the following example, which defines a weak absolute symbol "ext_addr_sym":
.weak ext_addr_sym
ext_addr_sym .set 0x12345678
If you assemble such assembly source and include the resulting object file in the link, the "ext_addr_sym" in this example is available as a weak absolute symbol in a final link. It is a candidate for removal if the symbol is not referenced elsewhere in the application.
.tab size
The .tab directive defines the tab size. Tabs encountered in the source input are translated to size character spaces in the listing. The default tab size is eight spaces.
In this example, each of the lines of code following a .tab statement consists of a single tab character followed by an NOP instruction.
Source file:
; default tab size
NOP
NOP
NOP
.tab 4
NOP
NOP
NOP
.tab 16
NOP
NOP
NOP
Listing file:
1 ; default tab size
2 00000000 00000000 NOP
3 00000004 00000000 NOP
4 00000008 00000000 NOP
5 .tab4
7 0000000c 00000000 NOP
8 00000010 00000000 NOP
9 00000014 00000000 NOP
10 .tab 16
12 00000018 00000000 NOP
13 0000001c 00000000 NOP
14 00000020 00000000 NOP
.text
The .text sets .text as the current section. Lines that follow this directive will be assembled into the .text section, which usually contains executable code. The section program counter is set to 0 if nothing has yet been assembled into the .text section. If code has already been assembled into the .text section, the section program counter is restored to its previous value in the section.
The .text section is the default section. Therefore, at the beginning of an assembly, the assembler assembles code into the .text section unless you use a .data or .sect directive to specify a different section.
For more information about sections, see Section 2.
This example assembles code into the .text and .data sections.
1 ******************************************
2 ** Begin assembling into .data section. **
3 ******************************************
4 00000000 .data
5 00000000 00000005 .byte 5,6
00000001 00000006
6
7 ******************************************
8 ** Begin assembling into .text section. **
9 ******************************************
10 00000000 .text
11 00000000 00000001 .byte 1
12 00000001 00000002 .byte 2,3
00000002 00000003
13
14 ******************************************
15 ** Resume assembling into .data section.**
16 ******************************************
17 00000002 .data
18 00000002 00000007 .byte 7,8
00000003 00000008
19
20 ******************************************
21 ** Resume assembling into .text section.**
22 ******************************************
23 00000003 .text
24 00000003 00000004 .byte 4
.title "string"
The .title directive supplies a title that is printed in the heading on each listing page. The source statement itself is not printed, but the line counter is incremented.
The string is a quote-enclosed title of up to 64 characters. If you supply more than 64 characters, the assembler truncates the string and issues a warning:
*** WARNING! line x: W0001: String is too long - will be truncated
The assembler prints the title on the page that follows the directive and on subsequent pages until another .title directive is processed. If you want a title on the first page, the first source statement must contain a .title directive.
In this example, one title is printed on the first page and a different title is printed on succeeding pages.
Source file:
.title "**** Fast Fourier Transforms ****"
; .
; .
; .
.title "**** Floating-Point Routines ****"
.page
Listing file:
TMS320C6000 Assembler Version x.xx Day Time Year
Copyright (c) 1996-2011 Texas Instruments Incorporated
**** Fast Fourier Transforms **** PAGE 1
2 ; .
3 ; .
4 ; .
TMS320C6000 Assembler Version x.xx Day Time Year
Copyright (c) 1996-2011 Texas Instruments Incorporated
**** Floating-Point Routines **** PAGE 2
No Errors, No Warnings
[stag] .union [expr]
[mem0] element [expr0]
[mem1] element [expr1]
. . .
. . .
. . .
[memn] .tag stag [exprn]
. . .
. . .
. . .
[memN] element [exprN]
[size] .endunion
label .tag stag
The .union directive assigns symbolic offsets to the elements of alternate data structure definitions to be allocated in the same memory space. This enables you to define several alternate structures and then let the assembler calculate the element offset. This is similar to a C union. The .union directive does not allocate any memory; it merely creates a symbolic template that can be used repeatedly.
A .struct definition can contain a .union definition, and .structs and .unions can be nested.
The .endunion directive terminates the union definition.
The .tag directive gives structure or union characteristics to a label, simplifying the symbolic representation and providing the ability to define structures or unions that contain other structures or unions. The .tag directive does not allocate memory. The structure or union tag of a .tag directive must have been previously defined.
Following are descriptions of the parameters used with the .struct, .endstruct, and .tag directives:
NOTE
Directives that Can Appear in a .union/.endunion SequenceThe only directives that can appear in a .union/.endunion sequence are element descriptors, structure and union tags, and conditional assembly directives. Empty structures are illegal.
These examples show unions with and without tags.
1 .global employid
2 xample .union ; utag
3 0000 ival .word ; member1 = int
4 0000 fval .float ; member2 = float
5 0000 sval .string ; member3 = string
6 0002 real_len .endunion ; real_len = 2
7
8 000000 .bss employid, real_len ;allocate memory
9
10 employid .tag xample ; name an instance
11 000000 0000- ADD employid.fval, A ; access union element
1
2 ; utag
3 0000 x .long ; member1 = long
4 0000 y .float ; member2 = float
5 0000 z .word ; member3 = word
6 0002 size_u .endunion ; real_len = 2
7
symbol .usect "section name", size in bytes[, alignment[, bank offset] ]
The .usect directive reserves space for variables in an uninitialized, named section. This directive is similar to the .bss directive; both simply reserve space for data and that space has no contents. However, .usect defines additional sections that can be placed anywhere in memory, independently of the .bss section.
Initialized sections directives (.text, .data, and .sect) tell the assembler to pause assembling into the current section and begin assembling into another section. A .usect or .bss directive encountered in the current section is simply assembled, and assembly continues in the current section.
Variables that can be located contiguously in memory can be defined in the same specified section; to do so, repeat the .usect directive with the same section name and the subsequent symbol (variable name).
For more information about sections, see Section 2.
This example uses the .usect directive to define two uninitialized, named sections, var1 and var2. The symbol ptr points to the first byte reserved in the var1 section. The symbol array points to the first byte in a block of 100 bytes reserved in var1, and dflag points to the first byte in a block of 50 bytes in var1. The symbol vec points to the first byte reserved in the var2 section.
Figure 5-8 shows how this example reserves space in two uninitialized sections, var1 and var2.
1 ***************************************************
2 ** Assemble into .text section **
3 ***************************************************
4 00000000 .text
5 00000000 008001A0 MV A0,A1
6
7 ***************************************************
8 ** Reserve 2 bytes in var1. **
9 ***************************************************
10 00000000 ptr .usect "var1",2
11 00000004 0100004C- LDH *+B14(ptr),A2 ; still in .text
12
13 ***************************************************
14 ** Reserve 100 bytes in var1 **
15 ***************************************************
16 00000002 array .usect "var1",100
17 00000008 01800128- MVK array,A3 ; still in .text
18 0000000c 01800068- MVKH array,A3
19
20 ***************************************************
21 ** Reserve 50 bytes in var1 **
22 ***************************************************
23 00000066 dflag .usect "var1",50
24 00000010 02003328- MVK dflag,A4
25 00000014 02000068- MVKH dflag,A4
26
27 ***************************************************
28 ** Reserve 100 bytes in var1 **
29 ***************************************************
30 00000000 vec .usect "var2",100
31 00000018 0000002A- MVK vec,B0 ; still in .text
32 0000001c 0000006A- MVKH vec,B0
.unasgsymbol
.undefinesymbol
The .unasg and .undefine directives remove the definition of a substitution symbol created using .asg or .define. The named symbol will removed from the substitution symbol table from the point of the .undefine or .unasg to the end of the assembly file. See Section 4.8.10 for more information on substitution symbols.
These directives can be used to remove from the assembly environment any C/C++ macros that may cause a problem. See Section 11 for more information about using C/C++ headers in assembly source.
.varsym1[, sym2, ... , symn]
The .var directive allows you to use substitution symbols as local variables within a macro. With this directive, you can 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.
See Section 4.8.10 for more information on substitution symbols .See Section 6 for information on macros.