cassemblynasmmixing

returning Assembly Function In C Code x86 Compilation on 64 bit linux


C code

#include <stdio.h>

int fibonacci(int);

int main()

{

    int x = fibonacci(3);

    printf("Fibonacci is : %d",x);

    return 0;
}

Assembly

section .text

global fibonacci

fibonacci:

    push ebp;
    mov ebp, esp;
    ; initialize
    mov dword [prev], 0x00000000;
    mov dword [cur], 0x00000001;
    mov byte [it], 0x01; 
    mov eax, dword [ebp + 8]; // n = 3
    mov byte [n], al;

getfib:

    xor edx,edx;
    mov dl, byte [n];
    cmp byte [it] , dl;
    jg loopend; 
    mov eax,dword [prev];
    add eax, dword [cur];
    mov ebx, dword [cur];
    mov dword [prev], ebx;
    mov dword [cur] , eax;
    inc byte [it];
    jmp getfib;

loopend:

    mov eax, dword [cur];

    pop ebp;

    ret;

section .bss

    it resb 1

    prev resd 1

    cur resd 1

    n resb 1

I was trying to run this assembly function in C code and on debugging , i saw that value in variable x in C code is right but there is some error coming when i use the printf function

Need Help on it

Command to compile:

nasm -f elf32 asmcode.asm -o a.o

gcc -ggdb -no-pie -m32 a.o ccode.c -o a.out

Click Below Pictures if they seem blurred

Below is debug before printf execute

Below is after printf execute


Solution

  • Your code does not preserve the ebx register which is a callee-preserved register. The main function apparently tries to do some rip-relative addressing to obtain the address of the format string for printf using ebx as a base register. This fails because your code overwrote ebx.

    To fix this issue, make sure to save all callee-saved registers before you use them and then restore their value on return. For example, you can do

    fibonacci:
    
        push ebp
        mov ebp, esp
        push ebx ; <---
    
        ...
    
        pop ebx ; <---
        pop ebp
        ret