J'essaie de faire un exercice simple de compilation. J'ai 1 fichier c 1 fichier d'assemblage et un makefile. quand j'exécute la commande 'make', j'obtiens l'erreur suivante :

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

Cela signifie que pour une raison quelconque, le programme c ne reconnaît pas la fonction ASM externe. Ce qui est encore plus étrange, c'est que lorsque j'exécute le même makefile sur les mêmes fichiers sur une machine différente, cela fonctionne comme un charme. J'aimerais vraiment que quelqu'un m'éclaire un peu sur ce truc. code 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;
}

Code 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             

Makefile:

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
0
MegaFlipFlop 21 mars 2021 à 17:15

2 réponses

Meilleure réponse

Vous n'avez pas besoin de déclarer la fonction external.

int do_Str(char*);

De plus, une fonction en C est préfixée par un trait de soulignement, vous devez donc la nommer en conséquence dans votre fichier asm.

    global _do_Str               
_do_Str:                             

Le trait de soulignement est automatiquement ajouté par le compilateur C, vous n'avez donc pas à l'utiliser dans le module C.

1
Devolus 21 mars 2021 à 14:19

La raison de votre erreur que vous citez ici est que votre ligne de compilation est erronée. Vous pouvez le dire parce que vous essayez de créer un fichier objet, mais que vous obtenez des erreurs de l'éditeur de liens, donc quelque chose ne va clairement pas :

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

Le problème est que vous avez oublié d'ajouter le drapeau -c à cette ligne de compilation, afin que le compilateur génère un fichier objet.

Cependant, dans votre makefile, le -c est présent, il est donc clair que cette erreur que vous citez n'est pas générée à partir du makefile que vous nous montrez.

exec: mainAssignment0.c libs
        gcc -g -m32 -c -o mainAssignment0.o mainAssignment0.c
0
MadScientist 21 mars 2021 à 14:41