How to use adress returned from call

Viewed 340

everybody!

I'm trying to make some project using assembly functions, which call from c. In c, I use errno.h. So I want to write errors, related with syscalls to errno for able to use perror etc. I know that syscall return to rax negative value if failed, so -rax = code of error.

in my errno.h error described as extern int *__error(void).

In my opinion if I detected, that return from syscall less than zero, i need to call ___error and after it I need to write -rax to return from ___error, but I don't know how.

I use macOS and NASM. To be more exact, there is a prototype my write func:

        global  _ft_write
        extern  ___error

_ft_write:
            mov rax, 0x2000004
            syscall
            cmp rax, 0
            jl errno
            ret

errno:
            call ___error
            mov rax, [rax]
            neg rax    
            ret

for compile: nasm -fmacho64

There is my main:

#include <stdio.h>
#include <errno.h>

int         main(void)
{
    printf("Write return: %d\n", ft_write(15, "wrong file descriptor", 3));
    printf("Error code: %d\n", errno);  return(1);
}

output: Write return: 9 Error code: 0

P. S. I'm new in assembly, sorry if question is stupid and thanks in advance.

1 Answers

__error returns an pointer to an int in rax. So you have to do two steps:

  1. Dereference pointer to get value
  2. Return -rax.

Dereference:

mov rax, [rax] ;Nearly equals to rax= (*rax)

Negate rax:

neg rax ; rax=-rax

Edit, based on your comments: Just use:

mov <someFreeRegister>, qword [rax]
neg <someFreeRegister>
mov qword [rax], <someFreeRegister>
Related