To use unified assembler language (UAL) in GNU as, place the .syntax unified
directive at the top of the file. To use it for inline assembly in C and C++, pass the -masm-syntax-unified
option to GCC.
GNU as documentation
GCC ARM options
Changes from earlier ARM assembly language
Change | Pre-UAL ARM syntax | Preferred UAL syntax |
---|---|---|
The default addressing mode for LDM and STM is IA |
LDMIA, STMIA |
LDM, STM |
You can use PUSH and POP mnemonics for full, descending stack operations in ARM in addition to Thumb. |
STMFD sp!, {reglist} LDMFD sp!, {reglist} |
PUSH {reglist} POP {reglist} |
You can use the LSL , LSR , ASR , ROR and RRX instruction mnemonics for instructions with rotations and no other operation, in ARM in addition to Thumb. |
MOV Rd, Rn, LSL shift MOV Rd, Rn, LSR shift MOV Rd, Rn, ASR shift MOV Rd, Rn, ROR shift MOV Rd, Rn, RRX |
LSL Rd, Rn, shift LSR Rd, Rn, shift ASR Rd, Rn, shift ROR Rd, Rn, shift RRX Rd, Rn |
Use the label form for PC-relative addressing. Do not use the offset form in new code. |
LDR Rd [pc, #offset] |
LDR Rd, label |
Specify both registers for doubleword memory accesses. You must still obey rules about the register combinations you can use. | LDRD Rd, addr_mode |
LDRD Rd, Rd2, addr_mode |
{cond} , if used, is always the last element of all instructions. |
ADD{cond}S LDR{cond}SB |
ADDS{cond} LDRSB{cond} |
Relaxation of requirements
Relaxation | Permitted syntax | Preferred syntax |
---|---|---|
If the destination register is the same as the first operand, zou can use a two register form of the instruction. | ADD r1, r3 |
ADD r1, r1, r3 |
Differences between pre-UAL Thumb syntax aand UAL syntax
Change | Pre-UAL Thumb syntax | Preferred UAL syntax |
---|---|---|
The default addressing mode for LDM and STM is IA |
LDMIA, STMIA |
LDM, STM |
You must use the S postfix on instructions that update the flags. This change is essential to avoid conflict with 32-bit Thumb instructions. |
ADD r1, r2, r3 SUB r4, r5, #6 MOV r0, #1 LSR r1, r2, #1 |
ADDS r1, r2, r3 SUBS r4, r5, #6 MOVS r0, #1 LSRS r1, r2, #1 |
The preferred form for ALU instructions specifies three registers, even if the destination register is the same as the first operand. However, the UAL syntax allows the two register syntax. | ADD r7, r8 SUB r1, #80 |
ADD r7, r7, r8 SUBS r1, r1, #80 |
If Rd and Rn are both Lo registers, MOV Rd, Rn is disassembles as ADDS Rd, Rn, #0 . |
MOV r2, r3 MOV r8, r9 CPY r0, r1 LSL r2, r3, #0 |
ADDS r2, r3, #0 MOV r8, r9 MOV r0, r1 MOVS r2, r3 |
NEG Rd, Rn is disassembled as RSBS Rd, Rn, #0 . |
NEG Rd, Rn |
RSBS Rd, Rn, #0 |
When using the LDR Rd, =const literal load pseudo-instruction, in pre-UAL syntax, the generated instruction might affect the condition code flags. In UAL syntax, the generated instruction sequence is guaranteed to not affect the condition code flags. |
LDR r0, =0 ; generates the instruction: MOVS r0, #0 |
LDR r0, =0 ; generates the instruction: LDR r0, [pc, #n] ... DCD 0 |
Optional hash with immediate constants
You do not have to specify a hash before an immediate constant in any instruction syntax. armasm
You always have to specify a hash before an immediate constant in divided
syntax. It is optional in unified
syntax. GNU as