I am curious - What is the difference between .equ
and .word
directives in ARM assembly, when defining constants?
4 Answers
.equ
is like #define
in C:
#define bob 10
.equ bob, 10
.word
is like unsigned int
in C:
unsigned int ted;
ted:
.word 0
Or initialized with a value:
unsigned int alice = 42;
alice:
.word 42

- 24,552
- 19
- 101
- 135

- 69,149
- 8
- 89
- 168
-
2and it has nothing to do with ARM it is true for most/all platforms supported by gnu assembler and other assemblers with those directives – old_timer Feb 07 '14 at 14:18
-
1Nitpicking :-) 1) `.word is like unsigned int in C`: but it does not set `st_size` as most C compilers, and it can be used anywhere, e.g. on the text section to generate code. 2) `.equ is like #define`: but it also generates an ABS symbol || More details: http://stackoverflow.com/a/33157659/895245 – Ciro Santilli OurBigBook.com Oct 15 '15 at 20:13
-
was just trying to relate to something the OP might understand, like but not exactly like, similar perhaps a better word than like? – old_timer Oct 15 '15 at 21:14
-
Also note that `.word` does *not* create a symbol. So it is rather like `malloc()`, imho. It just reserves a word of anonymous space wherever it appears. You can actually use it to generate instructions if you feel like puzzling together the bits of the opcodes. – Kamajii May 05 '19 at 11:19
-
@Kamajii doesn't .word always allocate 4 bytes of space? – Savannah Madison Jan 30 '21 at 09:45
.word is a directive that allocates a word-sized amount of storage space (memory) in that location. It can additionally have that location initialized with a given value.
.equ is more like a C preprocessor #define statement - it gets substituted in any subsequent code.
https://sourceware.org/binutils/docs-2.24/as/Equ.html#Equ
https://sourceware.org/binutils/docs-2.24/as/Word.html#Word
This is not actually ARM-specific, but applies to all gas targets.

- 5,852
- 1
- 33
- 40
-
3I just wanted to clarify that you can't use `.word` to initialize variables in RAM...you need something at runtime to do that. – Feb 07 '14 at 12:51
As mentioned in the accepted answer (written by old_timer) label: .word value
is like assigning a value to that label. I just want to add that you can assign multiple values to the same label just like an array, as the following:
g_pfnVectors:
.word _estack
.word Reset_Handler
.word NMI_Handler
.word HardFault_Handler
.word MemManage_Handler
...
The previous example has been taken from a STM32 MCU official startup file. This is exactly the machanism to initialize the NVIC.
So g_pfnVectors
label got multiple values assigned (as an array, where the values are aligned next to each other in the memory so to say).

- 14,913
- 17
- 70
- 99
NASM 2.10.09 ELF output:
.word
is simple: it outputs 2 bytes to the object file no matter where we are.Consequences of this:
- if
.word
is after a symbolx:
,x
will point to those bytes - if
.word
is in the text segment, those bytes might get executed
It has absolutely no other side effect. In particular, it does not set the
st_size
field of the symbol table entry (e.g.int
often == 4 bytes), which is something sensible compilers should do. You need the.size x, 2
directive for that.- if
.equ
does two things:- updates a macro-like variable
- the last time you call it, it generates a symbol with
st_shndx == SHN_ABS
and the given value
Sample code:
.text .equ x, 123 mov $x, %eax /* eax == 123 */ .equ x, 456 mov $x, %eax /* eax == 456 */
Now:
as --32 -o main.o main.S objdump -Sr main.o
Gives:
00000000 <.text>: 0: b8 7b 00 00 00 mov $0x7b,%eax 5: b8 c8 01 00 00 mov $0x1c8,%eax
which confirms the macro-like effect, and:
readelf -s main.o
contains:
Num: Value Size Type Bind Vis Ndx Name 4: 000001c8 0 NOTYPE LOCAL DEFAULT ABS x
which confirms the
SHN_ABS
effect: a symbol was created, and it could be used from another file by linking if it were global. I have explained this in more detail at https://stackoverflow.com/a/33148242/895245The situation is analogous for NASM's
equ
, except that the NASM version can only be used once per symbol..set
and the equals sign=
(source) are the same as.equ
.You should also look into
.equiv
https://sourceware.org/binutils/docs-2.25/as/Equiv.html , which prevents redefinition.

- 1
- 1

- 347,512
- 102
- 1,199
- 985