qt android 使用nasm 汇编引发的ld.lld: error: undefined symbol坑

使用nasm编译.asm文件
编译出来的函数前会附带_
例如函数名为test
那编译出来的.o文件导出函数为_test
这就会导致报错ld.lld: error: undefined symbol 找不到函数
需要为调用函数的地方在函数名前添加_

可以使用 nm命令查看.o文件导出的函数
windows下使用msys调用nm指令

在 Windows 平台上使用 x86 汇编编写程序时,若出现链接错误 `symbol '_printf' not defined`,通常是因为链接器无法找到 `printf` 函数的定义。该问题的根本原因在于链接阶段未正确链接 C 标准库(如 `msvcrt.lib`),或汇编代码中未正确声明外部符号。 ### 调用 `printf` 的前提条件 在 Windows x86 汇编程序中调用 `printf` 函数时,必须确保以下几点: - 使用 `extern printf` 声明该函数为外部符号; - 使用正确的调用约定(cdecl),即调用者负责清理栈空间; - 链接器需链接 `msvcrt.lib`,以提供 `printf` 的定义。 例如,以下是一个典型的调用方式: ```asm section .data msg db "Hello, World!", 0 section .text extern printf global _main _main: push msg call printf add esp, 4 ret ``` ### 链接器配置与依赖库 在链接阶段,若未指定 `-lmsvcrt` 或未通过 `gcc` 自动链接标准库,将导致 `printf` 无法解析。使用 `gcc` 链接时,可简化依赖处理: ```bash nasm -f win32 hello.asm gcc hello.o -o hello.exe -m32 ``` 此命令中,`-m32` 确保生成 32 位程序,`gcc` 会自动链接所需的运行时库,包括 `msvcrt.lib`,从而避免手动指定所有依赖项。 若使用 `ld` 手动链接,则需明确指定目标格式与依赖库: ```bash ld -m i386pe -o hello.exe hello.o -L"C:\TDM-GCC-32\x86_64-w64-mingw32\lib" -lmsvcrt ``` 其中 `-m i386pe` 指定目标格式为 32 位 Windows 可执行文件,`-lmsvcrt` 链接 Microsoft C 运行时库,提供 `printf` 的定义[^1]。 ### 常见错误与修复 若链接器报错 `undefined reference to 'printf'`,说明未正确链接 `msvcrt.lib`。解决方法包括: - 在链接命令中添加 `-lmsvcrt`; - 使用 `gcc` 替代 `ld` 以简化依赖处理; - 确保 TDM-GCC 工具链路径正确,且支持 32 位链接。 此外,若汇编代码中未使用 `extern printf` 声明,链接器也无法识别该符号,需确保函数声明与调用一致。 ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值