Reputation: 25096
I am learning assembly and a number of guides explain how to sys_write
but only using data stored in .text
. I want to print multiple ASCII characters stored on the stack.
global _start
section .data
section .text
_start:
push rbp
mov rbp, rsp
sub rsp, 16
mov QWORD [rbp], 47
mov QWORD [rbp - 8], 46
mov rax, 1
mov rdi, 1
lea rsi, [rbp]
mov rdx, 2
syscall
pop rbp
mov rax, 60
mov rdi, 0
syscall
The above code sets up the stack frame (useless for the example), makes room for the local variables and places the ASCII characters for 47 and 46 on the stack. Then it loads the address to the first ASCII character into rsi
and calls sys_write
. Finally, it calls sys_exit
.
However, when I run the code it only prints: /^@
. Running strace produces the following output:
execve("./a.out", ["./a.out"], 0x7ffd1d1c2280 /* 60 vars */) = 0
write(1, "/\0", 2/\0) = 2
exit(0) = ?
+++ exited with 0 +++
I feel like there's a fundamental misunderstanding I have concerning lea
or [rbp]
but I don't know enough assembly to know what I am missing.
Upvotes: 0
Views: 280
Reputation: 2927
I'm assuming this is on linux or something linux-like, but your read
is expecting a set of byte-packed chars, so the following change (keeping your 16 byte aligned stack)
sub rsp, 16
mov BYTE [rbp], 47
mov BYTE [rbp-1], 46
mov rax, 1
mov rdi, 1
lea rsi, [rbp-1]
mov rdx, 2
syscall
prints
./
Upvotes: 1