You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

.s文件程序退出码异常,手动调用exit触发段错误求助

x86-64汇编退出码异常与mov指令段错误排查

一、退出码为14的原因及修复

如果你的程序是通过write系统调用打印字符串,write执行后会将写入的字节数返回至%rax寄存器。若程序没有显式调用退出函数/系统调用,进程结束时会默认把%rax中的值作为退出码返回给系统。"Hello, world!\n"刚好是14字节,所以write返回14,最终退出码就是14。

修复方式:打印完成后显式触发退出流程:

  • 用系统调用直接退出(x86-64 Linux):
    .section .text
    _start:
        # 此处是write打印代码
        mov $0, %rdi    # 设置退出码为0
        mov $60, %rax   # 指定exit系统调用号
        syscall
    
  • 若基于libc编译(用gcc链接),在main函数末尾设置返回值后返回:
    mov $0, %eax
    ret
    

二、mov指令触发段错误的核心原因及修复

段错误的本质是执行了非法内存操作,你的情况大概率是以下几种问题:

1. 立即数语法错误(最常见)

AT&T汇编语法中,立即数必须加$前缀。如果你写的是mov 0, %rdi,汇编器会把0解析为内存地址,试图从地址0读取数据写入%rdi——而地址0属于无效内存,直接触发段错误。

正确写法:

mov $0, %rdi    # 64位赋值
# 或32位赋值(x86-64会自动零扩展到%rdi)
movl $0, %edi

2. 代码放置在非可执行段

如果你的mov指令写在了.data或.rodata段(这些段默认是不可执行的),当程序执行到该区域时,会因内存权限不足触发段错误。

修复:确保所有执行代码都放在.text段,开头必须声明:

.section .text
.global _start  # 或.global main,取决于链接方式
_start:
    # 你的代码逻辑

3. 程序入口设置错误

如果用gcc链接程序,入口点必须是main;如果直接用ld链接,入口点必须是_start。若入口指向了数据区域,执行到数据时会触发非法指令错误。

内容的提问来源于stack exchange,提问作者Basil

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.08 22:50:38