【问题标题】:link c and assembly链接 c 和程序集
【发布时间】:2015-07-07 18:52:53
【问题描述】:

我有一个非常简单的main.c 文件:

#include <stdio.h>
int cnt;
extern void increment();
int main()
{
    cnt = 0;
    increment();
    printf("%d\n", cnt);
    return 0;
}

还有更简单的hello.asm:

EXTERN cnt
section .text 
global increment 
increment:
  inc dword [cnt]
ret

首先我通过输入gcc -c main.c 得到main.o 然后我得到hello.o -- nasm -f macho hello.asm -DDARWIN 最后,为了得到一个可执行文件,我执行ld -o main main.o hello.o -arch i386 -lc 并得到一个错误:

ld: warning: -macosx_version_min not specified, assuming 10.10
ld: warning: 
ignoring file main.o, file was built for unsupported file format  (   0xCF 0xFA 0xED 0xFE 0x07 0x00 0x00 0x01 0x03 0x00 0x00 0x00 0x01 0x00 0x00 0x00 ) which is not the architecture being linked (i386): main.o
Undefined symbols for architecture i386:
  "_main", referenced from:
 implicit entry/start for main executable
"cnt", referenced from:
  increment in hello.o
ld: symbol(s) not found for architecture i386

如何解决此链接错误?

【问题讨论】:

  • @EOF 因为那不起作用? gcc 不知道调用 nasm
  • @Jester:是的,我刚刚意识到它不是用气体组件写的......
  • 您使用的是 64 位操作系统吗?然后为您的main.c 执行gcc -m32。根据@EOF 的建议,您也可以在获得hello.o 后使用gcc:gcc main.c hello.o(如有必要,添加-m32)。
  • @Jester with -m32 option I don't get file was built for unsupported file format error。但其他错误仍然存​​在。
  • 这可能有效,尝试在程序集文件中定义 cnt 像这样的数据部分 cnt dw 0 并通过在其上方添加 global cnt 使其像 increment 一样全局并删除 @ 987654342@线。现在在c 源代码中将int cnt 更改为extern int cnt,希望这应该让所有内容都能正确链接。

标签: c gcc assembly ld


【解决方案1】:
  • 指定架构(32/64 位,选项m32m64
  • 链接crt 文件,这些文件包含运行时 - 这是调用您的主函数的代码

修改你的 asm 文件:

EXTERN _cnt
section .text
global _increment
_increment:
  inc dword [_cnt]
ret

所以最后的命令行应该是:

gcc -c -m32 main.c
nasm -f macho hello.asm -DDARWIN
ld hello.o main.o /usr/lib/crt1.o  -lc -o main

检查拱门并执行:

file main
main: Mach-O executable i386

./main
1

【讨论】:

猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-08-01
  • 1970-01-01
相关资源
最近更新 更多