64-bit | 32-bit | 16-bit | 8-bit | |
%rax | %eax | %ax | %al | Often used for function return value |
%rbx | %ebx | %bx | %bl | callee-saved |
%rcx | %ecx | %cx | %cl | arg4 |
%rdx | %edx | %dx | %dl | arg3 |
%rsi | %esi | %si | %sil | "index" register, arg2 |
%rdi | %edi | %di | %dil | arg1; see BOH p 245 |
%rbp | %ebp | %bp | %bpl | "base pointer", not always needed; callee-saved |
%rsp | %esp | %sp | %spl | stack pointer; some special hardware implications |
%r8 | %r8d | %r8w | %r8b | arg5; r8-r15 were added with x86-64 |
%r9 | %r9d | %r9w | %r9b | arg6 |
%r10 | %r10d | %r10w | %r10b | |
%r11 | %r11d | %r11w | %r11b | |
%r12 | %r12d | %r12w | %r12b | callee-saved |
%r13 | %r13d | %r13w | %r13b | callee-saved |
%r14 | %r14d | %r14w | %r14b | callee-saved |
%r15 | %r15d | %r15w | %r15b | callee-saved |
%rip | the instruction pointer; not directly available |
callee-saved register: if P calls Q, and Q wants to modify the register,
Q is responsible for saving it on entry and restoring it on exit.
caller-saved register: if P calls Q, and P has something in the register
it will need later, then P must save it first. Q is not responsible.
Move instructions (and most others) must have at least one operand be a
register; memory-to-memory moves are disallowed.
First operand is the source, second operand is the destination
immediate | movl $13, %eax | move decimal 13 into eax hex immediate operands use $0xdeadbeef format |
immediate src, indirect dest | movl 0x25,(%rdi) | move 37 to address pointed to by %rdi |
memory absolute | movl $0xdeadbeef,%eax | seldom used, except to probe certain fixed
addresses |
memory indirect | movl (%rbx), %rax | copy memory pointed to by %rbx to %rax |
base+displacement | movl 100(%rbx),%rax | copy memory 100 bytes past where %rbx points copy to %rax |
indexed | movl (%rbx,%rdi),%rax | memory at address %rbx+%rdi |
indexed with displacement | movl 16(%rbx,%rdi), %rax |
memory at address %rbx+%rdi + 16 |
scaled indirect | movl (,%rdi,4),%rax | memory address at 4*%rdi. Rare. Note comma. |
scaled indexed | movl (%rbx,%rdi, 4),%rax | memory address at %rbx + 4*%rdi. Common with arrays. |
scaled indirect with displacement |
||
scaled indexed with displacement |
movb/movw/movl/movq: move data from source to destination of the same size
movzbw, movzbl, movzwl, movzbq, movzwq: move from shorter to longer (b = 8 bit, w=16bit, l=32bit, q=64 bit), extending with zeros movs does the same but with sign-extension.
pushq S Push 64-bit value S onto the stack; decrement
%rsp by 8
popq D Pop 64-bit value from stack and place into
D; increment %rsp by 8
ret Pop
return address from stack and jump there
Unary: inc D, dec D: increment and decrement
leaq S,D: Load effective address of S into D
add S,D: Add S to D
sub S,D: Subtract S from D
imul S,D: Multiply D by S; 64-bit result
(there is no 64-bit-source divide instruction)
xor S,D: D is assigned S xor D
or S,D: D is the logical
or of S and D
and S,D likewise
sal k,D left shift D by k
bits; same as shl
sar k,D right shift D by k bits,
adding copies of the sign bit at left
shr k,D right shift D by k
bits, adding zero bits at left
Condition codes, set by add and sub (but not lea)
cmpb, cmpw, cmpl, cmpq. cmpq S,D asks "how does D compare to S", as if it computed D-S. See jg and jl below.