web-dev-qa-db-fra.com

En programmation C, qu'est-ce que l'erreur `référence indéfinie`, lors de la compilation?

J'ai ce programme simple suivant que je suis en train de compiler sous Linux Ubuntu.

Main.c:

#include <stdio.h>
#include "Person.h"

int main()
{   
    struct Person1 p1 = Person1_Constructor(10, 1000);
}

Person.c:

#include <stdio.h>
#include "Person.h"

struct Person1 Person1_Constructor(const int age, const int salary)
{
    struct Person1 p;
    p.age = age;
    p.salary = salary;
    return p;
};

Person.h:

struct Person1
{
    int age, salary;
};
struct Person1 Person1_Constructor(const int age, const int salary);

Pourquoi ai-je le message error suivant?

/tmp/ccCGDJ1k.o: In function `main':
Main.c:(.text+0x2a): undefined reference to `Person1_Constructor'
collect2: error: ld returned 1 exit status

J'utilise gcc Main.c -o Main pour compiler.

6
dimitris93

Lorsque vous liez le programme, vous devez donner Main.o et Person.o en tant qu’entrées.

La construction se fait généralement en deux étapes (1) compilation et (2) mise en relation . Pour compiler vos sources, procédez comme suit:

$ gcc -c -o Main.o Main.c
$ gcc -c -o Person.o Person.c

Ou en une ligne:

$ gcc -c Main.c Person.c

Ensuite, les fichiers objets résultants doivent être liés dans un seul exécutable:

$ gcc -o Main Main.o Person.o

Pour les petits projets, de quelques unités de compilation comme la vôtre, les deux étapes peuvent être effectuées en une invocation gcc:

$ gcc -o Main Main.c Person.c

les deux fichiers doivent être donnés car certains symboles dans Person.c sont utilisés par Main.c.

Pour les projets plus importants, le processus en deux étapes permet de ne compiler que ce qui a changé lors de la génération de l'exécutable. Généralement, cela se fait à travers un Makefile.

4
Diego

Le problème est probablement dû au fait que vous ne compilez que Main.c lorsque vous devez compiler Main.c et Person.c en même temps. Essayez de le compiler en tant que gcc Main.c Person.c -o MyProgram.

Chaque fois que vous avez plusieurs fichiers, ils doivent tous être spécifiés lors de la compilation afin de résoudre les références externes, comme c'est le cas ici. Le compilateur crache des fichiers objets qui seront ensuite liés à un exécutable. Découvrez ce tutoriel sur les makefiles: Tutoriel Make File Il est utile d’automatiser ce processus. 

1
Mlagma