从汇编函数调用返回到 C 程序时如何处理堆栈指针寄存器?

问题描述

我的程序由两个文件组成:main.c和core.s,运行在lubuntu linux的32位虚拟机上。

Main.c 接受一个整数并将其传递给汇编函数 void printFunc(int x)。汇编函数依次调用 C 函数来检查 x 的奇偶校验。如果 x 是偶数,函数将打印 4x,如果 x 是奇数,它将打印 8x。打印调用必须在汇编函数内完成。

section .text
    global printFunc
    extern c_checkValidity
    extern printf

section .data       ; data section

fmt: db "%d",10,0 ; The printf format,"\n",'0'
            
printFunc:
    push ebp                ; code for handling stack I've seen from
    mov ebp,esp            ; other examples online
    pushad                  
    mov ebx,eax            ; copy and input value
    push eax                ; Move input onto stack
    call c_checkValidity    ; Call C function,return value is in eax   
    cmp eax,1              ; Check result,1 indicates even
    je multby4              ; If even,do mult by 4
    jmp multby8             ; Otherwise odd,do mult by 8

multby4:                    ;INPUT WAS EVEN
    sal ebx,2              ; left shift by 2 is equivalent to multiplying by 4 
    jmp exitcode            ; print and exit code

multby8:                    ;INPUT WAS ODD
    sal ebx,3              ; left shift by 3 is equivalent to multiplying by 8
    jmp exitcode            ; print and exit code
    
exitcode:   
    mov eax,ebx             ; move value to eax to keep as default return value of func
    push ebx                ; Push final answer to the stack
    push dword fmt          ; Push print format to the stack
    call printf             ; Print answer
    mov eax,ebx            ; copy final answer as return value
    popad
    mov esp,ebp            ; return stack pointer to what it was before operation
    pop ebp                 ; get rid of saved pointer
    ret                     ; return state to caller

整数输入被接收,奇偶校验测试,并正确打印到标准输出call printf 成功执行后,某处发生段错误。当我使用 gdb 尝试回溯段错误时,报告显示“exitcode () 中的 0x0804a0f”。想必这就是导致segfault的运行时代码的地址?

我很清楚我未能以某种方式正确处理堆栈指针寄存器(尤其是?)。我已经尝试在此站点和其他站点搜索有关如何在将控制权返回给调用者之前正确寻址堆栈的示例,但无济于事。当然,我很乐意使代码工作,并且对如何修复代码的任何建议表示赞赏,但我主要是要求解释我应该跟踪和维护的内容,以便从汇编函数返回到调用者(额外感谢如果该解释包括如何将值传回给调用者)。

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)