如何链接ELF32程序集和C文件?

时间:2011-04-10 14:43:36

标签: c assembly compilation nasm

我在C中编写了一个简单的汇编软件(nasm)和一个简单的应用程序。 我的C代码从汇编代码调用一个函数,但我不知道如何编译C代码而没有从'extern int Sum();'中收到'undefined reference'错误。线。

C代码:

#include <stdio.h>

extern int Sum();

main()
{
  int a1, a2, x;

  x = Sum(a1, a2);
  printf("value of x is: %d\n", x);
}

汇编代码:

global _Sum

_Sum:
    push ebp
    mov  ebp, esp

    mov  eax, [ebp+8]
    mov  ecx, [ebp+12]
    add  eax, ecx
    pop  ebp
    ret

我如何单独编译这两个文件并将它们一起链接到一个统一的文件中?

6 个答案:

答案 0 :(得分:2)

您应该组装.asm文件以获取.o(对象)文件,正如您所说的那样。然后你应该编译(但不链接).c文件来获取另一个.o文件,如下所示:

gcc -o whatever.o -c whatever.c

然后你应该将它们链接在一起,如下所示:

gcc whatever.o asm.o

然后链接器将立即运行所有目标代码,并且应该能够解析它所需的引用。

答案 1 :(得分:2)

在与ELF一起使用的ABI中,C名称不会受到初始_的限制。

答案 2 :(得分:1)

有两种可能性来解决这个问题,将C源代码编译为C(NOT C ++),将其编译为C,你必须给它扩展名.c

第二种方式,在C ++代码(扩展名.cpp)中名称被破坏,当您编译C ++代码时,使用十六进制编辑器查看目标文件并搜索Sum。就我而言,名称变为_Z3Sumii。如果您将汇编程序源中的名称更改为此名称,您会发现它可以正常工作。

同时将C ++源代码中的extern语句更改为以下内容,因为它需要两个类型为int的参数,例如extern int Sum(int, int);

  global _Z3Sumii
_Z3Sumii:
  push ebp
  mov  ebp, esp
  mov  eax, [ebp+8]
  mov  ecx, [ebp+12]
  add  eax, ecx
  mov  esp, ebp
  pop  ebp
  ret

编译:

gcc -c file.cpp
nasm -f elf32 sum.asm -o sum.o
gcc file.o sum.o -o file

答案 3 :(得分:1)

对于来这里搜索的人:查看代码并预订http://www.drpaulcarter.com/pcasm/index.php :在here上下载linux示例:您要引用的文件是first.asm - (根据体系结构编译:下面的32位示例)

nasm -f elf -d ELF_TYPE asm_io.asm
nasm -f  elf32 first.asm 
gcc -o first first.o driver.c asm_io.o

答案 4 :(得分:0)

最本机的方法是使用GCC工具链获取C程序的汇编代码,然后手动汇编两个汇编程序文件并链接它们。

答案 5 :(得分:0)

在您的情况下:

nasm -f elf -o sumasm.o sumasm.asm
gcc -o sum sumasm.o sum.c 

您可能需要elf32