Не удается найти источник ошибки разрыва сегментации - PullRequest
0 голосов
/ 28 марта 2019

Мы должны кодировать рекурсивную функцию fibbonachi, используя стек в качестве домашней работы.Поскольку у меня нет никакого способа запустить код NASM непосредственно на моем ноутбуке, я использовал браузерные компиляторы, такие как jdoodle и кодирование, чтобы проверить работоспособность и отладку моего кода.После целого дня безостановочной работы я не могу понять, почему мой код все еще вызывает ошибку ошибки сегментации.

Я шаг за шагом проанализировал структуру стека и не могу найти там ошибку.Возможно, я упускаю что-то очевидное, так как я все еще изучаю NASM и не совсем понял некоторые концепции.Ошибка также может быть в онлайн-браузере или, по крайней мере, в том, как он обрабатывает вывод: я обычно использую printf, но я пытался повторно использовать пример кода, который они предоставляют.

Для целей отладки значение R равновошел с мов мечом [R].Кроме того, поскольку в выводе dosent используется printf, он выводит awnser как ascii characther, где ascii code of characther - это выведенное число.

section .text

global _start

fib:

    ;ret    <- esp
    ;R      
    ;ebps
    ;???    <- ebp?

    cmp dword[esp + 4], 4
    JS TroisOuMoins

    mov dword[ebx], esp
    add dword[ebx], 8
    push dword[ebx]

    ;ebps'  <- esp
    ;ret    
    ;R      
    ;ebps
    ;???    <- ebp?

    mov ebp, dword[esp]

    ;ebps'   <- esp
    ;ret
    ;R
    ;ebps   <- ebp

    sub dword[esp + 8], 1  ; R = R - 1
    push dword[esp + 8]

    ;R'     <- esp
    ;ebps'  
    ;ret
    ;R
    ;ebps   <- ebp

    call fib

    ;fib1    <- esp
    ;ebps'  
    ;ret
    ;R
    ;ebps   <- ebp

    push dword[esp]

    ;fib1   <- esp
    ;fib1    
    ;ebps'  
    ;ret
    ;R
    ;ebps   <- ebp

    mov ebx, dword[esp + 16]
    mov dword[esp + 4], ebx
    pop dword[esp + 16]
    dec dword[esp]

    ;R'     <- esp
    ;ebps'  
    ;ret
    ;fib1
    ;ebps   <- ebp

    call fib

    ;fib2   <- esp
    ;ebps'  
    ;ret
    ;fib1
    ;ebps   <- ebp

    mov ebx, dword[esp]
    add dword[esp + 12], ebx
    sub esp, 8

    ;ret    <- esp
    ;fibTotal
    ;ebps   <- ebp

    mov ebp, dword[ebp]

    ;ret    <-esp
    ;fibTotal
    ;ebps
    ;???    <-ebp?

    TroisOuMoins:

ret

_start:
    push ebp            ; --> 1 - sauvegarder l'état de la pile et du record d'activation présent (le contenu du ebp est mis sur la pile)
    mov ebp, esp            ; Mettre la valeur du "stack pointer" dans le "base pointer".


    mov dword[R], 4

    push ebp

    push dword[R]

    call fib

    pop dword[R]

    mov ebp, dword[esp]
    sub esp, 4

    mov esp, ebp
    pop ebp             ; <-- 1- restauration du ebp original

    mov     ebx, dword[R]
    mov     [sum], ebx

    mov     ecx, msg
    mov     edx, len
    mov     ebx, 1
    mov     eax, 4
    int     0x80

    mov     ecx, sum
    mov     edx, 1
    mov     ebx, 1
    mov     eax, 4
    int     0x80

    mov     eax, 1
    int     0x80


section .data
    R:          times 4 db 0 ; 32-bits integer = 4 bytes
    msg db  "Fibbonachi is "
    len equ $ - msg

segment .bss

    sum resb 1

Код работает для случаев 1, 2 и 3,в соответствии с проектом (функция пропускает рекурсивные вызовы для случаев 1, 2 и 3, поэтому проблема, вероятно, лежит внутри.).Любое число выше 4 приводит к ошибке «ошибка сегментации».Ожидаемый результат - соответствующее число Фиббоначи для ввода.

...