【问题标题】:C makefile issue, undefined reference to functionC makefile 问题,未定义的函数引用
【发布时间】:2021-06-18 08:25:43
【问题描述】:

我试图在编译中做一个简单的练习。 我有 1 个 c 文件、1 个程序集文件和一个 makefile。 当我运行“make”命令时,出现以下错误:

gcc -g -m32 -Wall -o mainAssignment0.o mainAssignment0.c
/tmp/ccXfVxtg.o: In function `main':
/home/caspl202/Desktop/tasks/Assignment0/mainAssignment0.c:12: undefined reference to `do_Str'
collect2: error: ld returned 1 exit status
makefile:10: recipe for target 'mainAssignment0.o' failed
make: * [mainAssignment0.o] Error 1

意味着由于某种原因,c 程序无法识别外部 ASM 函数。 更奇怪的是,当我在不同机器上的相同文件上运行相同的 makefile 时,它​​就像一个魅力。我真的很希望有人能对这件事有所了解。 C代码:

#include <stdio.h>
#define MAX_LEN 100         
extern int do_Str(char*);
int main(int argc, char** argv) {
  char str_buf[MAX_LEN];   
  int counter = 0;
  fgets(str_buf, MAX_LEN, stdin);   
  counter = do_Str (str_buf);       
  printf("%s%d\n",str_buf,counter); 
  return 0;
}

ASM 代码:

section .data                       
        an: dd 0                    
section .text                       
        global do_Str               
do_Str:                             
        push ebp                    
        mov ebp, esp                 
        pushad                      
        mov ecx, dword [ebp+8]              
    loop:           
        cmp byte [ecx], 32
        jnz noS
        inc dword [an] 
    noS:
        cmp byte [ecx], 65
        jl noC
        cmp byte [ecx], 90
        jg noC
        add byte [ecx], 32
    noC:
        inc ecx                 
        cmp byte [ecx], 0       
        jnz loop
        popad                       
        mov eax,[an]                
        mov esp, ebp            
        pop ebp              
        ret             

生成文件:

all: exec
libs: asm-lib
asm-lib: asmAssignment0.s
    nasm -g -f elf -o asmAssignment0.o asmAssignment0.s
exec: mainAssignment0.c libs
    gcc -g -m32 -c -o mainAssignment0.o mainAssignment0.c
    gcc -g -m32 -o Assignment0.out mainAssignment0.o asmAssignment0.o 
.PHONY: clean
clean:
    rm -rf ./*.o Assignment0.out

【问题讨论】:

标签: c makefile


【解决方案1】:

您不需要将函数声明为外部。

int do_Str(char*);

此外,C 中的函数前缀为下划线,因此您必须在 asm 文件中相应地命名它。

    global _do_Str               
_do_Str:                             

下划线是由 C 编译器自动添加的,因此您不必在 C 模块中使用它。

【讨论】:

    【解决方案2】:

    您在此处引用错误的原因是您的编译行错误。您可以判断,因为您正在尝试创建一个目标文件,但从链接器收到错误,所以显然有些地方不对:

    gcc -g -m32 -Wall -o mainAssignment0.o mainAssignment0.c
      ...
    collect2: error: ld returned 1 exit status
    

    问题是你忘记在这个编译行添加-c标志,让编译器生成一个目标文件。

    但是,在您的 makefile 中存在 -c,因此很明显,您引用的这个错误不是从您向我们展示的 makefile 生成的。

    exec: mainAssignment0.c libs
            gcc -g -m32 -c -o mainAssignment0.o mainAssignment0.c
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-12-03
      • 1970-01-01
      • 2018-10-20
      • 1970-01-01
      • 2022-01-16
      • 2021-11-14
      • 2010-11-16
      相关资源
      最近更新 更多