As a preface, I'm running this on a 64-bit Linux OS and am thus using the 64-bit Linux syscalls.
strlen procedure takes
rdi as a parameter and returns the length of the string
excluding \0 in
rax. (You have to enter a string that ends with \0). I have tested this procedure and know it works correctly.
puts procedure takes
rdi as its parameter, uses
strlen to get the length and then uses the
Here is a (hopefully) minimal reproducible example:
section .data msg db "HELLO", 10, 0 section .text global _start _start: mov rdi, msg call puts mov rax, 0x3c xor rdi, rdi syscall strlen: push rdi push rcx push rsi xor rax, rax mov rcx, 0xffffffff repnz scasb jnz .error not rcx dec rcx mov rax, rcx .return: pop rsi pop rcx pop rdi ret .error: mov rax, -1 jmp .return puts: mov rsi, rdi call strlen mov rdx, rax mov rax, 1 mov rdi, rax syscall ret
I'm really confused as to why this isn't working. My
puts procedure is just a simple syscall really, so I honestly don't know what is going wrong here.
I have tested [my
strlen] and know it works correctly.
I'm afraid not.
mov rcx, 0xffffffff
You seem to be thinking this loads
-1, but it doesn't:
-1 as a 32-bit signed integer, but
rcx is a 64-bit register. (Maybe you copied from some 32-bit code?) In particular,
mov rcx, 0xffffffff followed by
not rcx does not result in
0, but rather
0xffffffff00000000. As a result your
strlen returns a seriously incorrect value.
Change this to
mov rcx, -1 or
mov rcx, 0xffffffffffffffff.
User contributions licensed under CC BY-SA 3.0