Installation de la bibliotheque readline/history

Signaler
Messages postés
108
Date d'inscription
samedi 31 mars 2012
Statut
Membre
Dernière intervention
16 juin 2013
-
Messages postés
1309
Date d'inscription
samedi 31 janvier 2009
Statut
Membre
Dernière intervention
5 juin 2013
-
Bonsoir tout le monde,
j'ai écrit un programme qui utilise readline:

char *seq;
add_history(seq);

et quand je compile, il y a une erreur: undefined reference to 'add_history'
j'ai bien inclus #include<readline/history.h>
#include<readline/readline.h>
dans l'installation j'ai mis: sudo apt-get install libreadline6 libreadline6-dev
Pourriez-vous m'aider....

Merci d'avance !!!

3 réponses

Messages postés
1309
Date d'inscription
samedi 31 janvier 2009
Statut
Membre
Dernière intervention
5 juin 2013
12
Salut,

A première vue tu n'as pas linké avec la lib. Tu peux montrer comment tu t'y prend pour compiler stp ?
Messages postés
108
Date d'inscription
samedi 31 mars 2012
Statut
Membre
Dernière intervention
16 juin 2013

Au faite j'ai plusieurs fonctions donc j'ai mon Makefile j'ai vu dans d'autres forums que l'erreur n'est pas dans le include mais un probléme linkage à vrai dire je ne comprends pas trop ce terme "linké"
voici mon makefile:

all : minish

cmd.o : Pipe.h var_interne.h detecteur_commande.h prototype.h cmd.c
gcc -c -g cmd.c


detecteur_commande.o : detecteur_commande.h prototype.h detecteur_commande.c
gcc -c -g detecteur_commande.c


gestion_var.o : prototype.h gestion_var.h Pipe.h gestion_var.c
gcc -c -g gestion_var.c

var_interne.o : var_interne.h prototype.h var_interne.c
gcc -c -g var_interne.c

gestion_redirection.o : gestion_redirection.h prototype.h gestion_redirection.c
gcc -c -g gestion_redirection.c

pipe.o : Pipe.h prototype.h Pipe.c
gcc -c -g Pipe.c

minish : cmd.o detecteur_commande.o Pipe.o var_interne.o gestion_redirection.o gestion_var.o
gcc gestion_var.o gestion_redirection.o var_interne.o Pipe.o cmd.o detecteur_commande.o -o minish

clean : rm -f gestion_var.o gestion_redirection.o var_interne.o cmd.o detecteur_commande.o cmd
Messages postés
1309
Date d'inscription
samedi 31 janvier 2009
Statut
Membre
Dernière intervention
5 juin 2013
12
Ok, tu as encore quelques trucs à apprendre concernant la compilation et les makefile, mais on est là pour apprendre :)

Niveau compilation, petit rappel (très simplifié) sur les 3 phases principales :
1. Passage du préprocesseur.
2. Compilation de chaque fichier C en un beau fichier objet.
3. Assemblage de tous les fichiers objets pour former un bel exécutable. Cette phase se nomme l'édition des liens (linking).

Bref, avec gcc -c tu vas procéder au passage du préprocesseur et à al compilation de chaque fichier C. Ensuite, tu as un dernier appel à gcc qui va faire l'édition des liens. Si al compilation se passe bien, c'est cette édition des liens qui foire chez toi. Pourquoi ?
Lorsque tu as fait ton include, c'était une simple directive de préprocesseur. À ce moment le préprocesseur à ajouter le contenu du fichier .h correspondant, et ce fichier contient uniquement les déclarations des fonctions. Comme ça, lors de la compilation, le fait d'avoir déclarer les fonctions permet de dire au compilo "cette fonction existe mais elle est autre part".
Ce qu'il te manque, c'est à l'édition des liens que tu dois le faire. Les fonctions en elles mêmes de la bibliothèque que tu utilise sont de simpels fichiers objets réunis dans une archive. Tu dois donc dire au linker où se trouve cette archive afin qu'il puisse tout assembler comme il faut. Pour ceci tu as l'option -l (un L minuscule) pour indiquer la bibliothèque à utiliser. Ici ce sera certainement quelque chose du genre "-l readline".

Tu devrais modifier ta ligne de comme suit :
gcc gestion_var.o gestion_redirection.o var_interne.o Pipe.o cmd.o detecteur_commande.o -o minish -l readline


Maintenant au niveau du makefile...
Créer une règle pour chaque fichier source... c'est abominable. Il y a moyen de généraliser ça. En particulier avec l'utilisation de "variables" :
NAME = minish
CC = gcc
CFLAGS = -g
LD = gcc
LDFLAGS = -o $(NAME) -l readline
RM = rm -f
SRC = gestion_var.c\
gestion_redirection.c\
var_interne.c\
Pipe.c cmd.c\
detecteur_commande.c
OBJ = $(SRC:.c=.o)

$(NAME) : all

all : $(OBJ)
$(LD) $(OBJ) $(LDFLAGS)

clean :
$(RM) $(NAME) $(OBJ)

Pour expliquer un peu :
Nous avons surtout défini des variables :
- NAME : le nom de ton projet
- CC : le compilateur (ici gcc)
- CFLAGS : les flags à utiliser pour compiler (le -c sera fait automatiquement)
- LD : le linker, ici encore gcc
- LDFLAGS : les flags pour l'édition des liens on a donc le -o minish, enfin en utilisant $(NAME) ainsi que le -l readline que l'on a vu plus tôt.
- RM : juste pour définir ce qui va supprimer les fichiers afin de faire le ménage
- SRC : on liste tous les fichiers source
- OBJ : on liste tous les fichiers objets. Astuce, on utilise la liste des sources en spécifiant qu'il faut remplacer .c par .o pour obtenir le nom des fichiers objet.

Maintenant les règles.
La règle $(NAME), donc minish, sert juste à appeler all.
La règle clean sert à faire le ménage (c'est une bonne pratique que de la mettre).
Le plus intéressant : la règle all. Elle dépend des objets. Or, vu que l'on a défini SRC, CC et CFLAGS, make sais comment passer d'un .c en .o et va donc générer tout seul les .o (il y a une règle nommée .c.o par défaut qui permet ceci, tu peux en créer une afin de la modifier mais ici ce n'est pas nécessaire). Il ne nous reste plus qu'a linker, ce qui est fait avec la commande.