Systèmes d’Exploitation I - Travaux Pratiques 0

Programming, Makefiles, Compilation · lab

Voir tous les documents en programmation

Systèmes d’Exploitation I

Travaux Pratiques 0

ÉTUDE PRÉLIMINAIRE

La compilation avec Make

Amine DHRAIEF

make

● make est un logiciel qui construit automatiquement des fichiers, souvent

exécutables, ou des bibliothèques à partir d'éléments de base tels que

du code source.

● Il utilise des fichiers appelés makefile (Makefile) qui spécifient comment

construire les fichiers cibles.

● À la différence d'un simple script shell, make exécute les commandes

seulement si elles sont nécessaires.

– Le but est d'arriver à un résultat (logiciel compilé ou installé, documentation créée, etc.)

sans nécessairement refaire toutes les étapes.

● make est particulièrement utilisé sur les plateformes UNIX.

18/01/18

2

make

● make sert principalement à faciliter la compilation et l'édition

de liens puisque dans ce processus le résultat final dépend

d'opérations précédentes.

● Pour ce faire, make utilise un fichier de configuration appelé

makefile qui porte souvent le nom de Makefile. Ce dernier

décrit des cibles (qui sont souvent des fichiers, mais pas

toujours), de quelles autres cibles elles dépendent, et par

quelles actions (des commandes) y parvenir.

● make cherche dans le répertoire courant le makefile à utiliser.

18/01/18

3

make

● Un Makefile est un fichier constitué de plusieurs règles de la forme :

cible: dependance

[tab] commandes

● Chaque commande est précédée d'une tabulation.

● Lors de l'utilisation d'un tel fichier via la commande make la première règle

rencontrée, ou la règle dont le nom est spécifié, est évaluée. L'évaluation

d'une règle se fait en plusieurs étapes :

Publicité

– Les dépendances sont analysées, si une dépendance est la cible d'une autre règle du

Makefile, cette règle est à son tour évaluée.

– Lorsque l'ensemble des dépendances est analysé et si la cible ne correspond pas à un

fichier existant ou si un fichier dépendance est plus récent que la régle, les différentes

commandes sont exécutées.

18/01/18

4

Exemple

● hello.c

#include <stdio.h>

#include <stdlib.h>

void Hello(void)

printf("Hello World\n");

{

}

18/01/18

5

Exemple

● hello.h

void Hello(void);

18/01/18

6

Exemple

● main.c

#include <stdio.h>

#include <stdlib.h>

#include "hello.h"

int main(void)

{

}

Hello();

return EXIT_SUCCESS;

18/01/18

7

Exemple

● Makefile

hello: hello.o main.o

gcc -o hello hello.o main.o

Publicité

hello.o: hello.c

gcc -o hello.o -c hello.c -W -Wall -ansi

-pedantic

main.o: main.c hello.h

gcc -o main.o -c main.c -W -Wall -ansi -pedantic

8

18/01/18

Exemple

● Nous cherchons à créer le fichier exécutable hello, la première

dépendance (hello.o) est la cible d'une des règles de notre Makefile, nous

évaluons donc cette règle. Comme aucune dépendance de hello.o n'est

une règle, aucune autre règle n'est à évaluer pour compléter celle-ci.

● Deux cas se présentent ici : soit le fichier hello.c est plus récent que le

fichier hello.o, la commande est alors exécutée et hello.o est construit,

soit hello.o est plus récent que hello.c est la commande n'est pas

exécutée. L’évaluation de la règle hello.o est terminée.

● Les autres dépendances de hello sont examinées de la même manière

puis, si nécessaire, la commande de la règle hello est exécutée et hello

est construit.

18/01/18

9

Exemple

● Plusieurs cas ne sont pas gérés dans l'exemple précédent :

– Un tel Makefile ne permet pas de générer plusieurs exécutables distincts.

– Les fichiers intermédiaires restent sur le disque dur même lors de la mise en production.

– Il n'est pas possible de forcer la regénération intégrale du projet

● Ces différents cas conduisent à l'écriture de règles complémentaires :

– all : généralement la première du fichier, elle regroupe dans ces dépendances

l'ensemble des exécutables à produire.

– clean : elle permet de supprimer tout les fichiers intermédiaires.

– mrproper : elle supprime tout ce qui peut être régénéré et permet une reconstruction

complète du projet.

● En ajoutant ces règles complémentaires, notre Makefile devient donc :

18/01/18

10

Makefile

all: hello

Exemple

Publicité

hello: hello.o main.o

gcc -o hello hello.o main.o

hello.o: hello.c

gcc -o hello.o -c hello.c -W -Wall -ansi -pedantic

main.o: main.c hello.h

gcc -o main.o -c main.c -W -Wall -ansi -pedantic

clean: rm -rf *.o

mrproper: clean

rm -rf hello

18/01/18

11

Exemple

● Il est possible de définir des variables dans un Makefile, ce qui rend les

évolutions bien plus simples et plus rapides, en effet plus besoin de

changer l'ensemble des règles si le compilateur change, seule la variable

correspondante est à modifier.

● Une variable se déclare sous la forme NOM=VALEUR et se voir utiliser via

$(NOM).

– Nous allons donc définir quatre variables dans notre Makefile :

● Une désignant le compilateur utilisée nommée CC (une telle variable est

typiquement nommé CC pour un compilateur C, CXX pour un compilateur

C++).

– CFLAGS regroupant les options de compilation (Généralement cette variable est

nommées CFLAGS pour une compilation en C, CXXFLAGS pour le C++).

– LDFLAGS regroupant les options de l'édition de liens.

– EXEC contenant le nom des exécutables à générer.

18/01/18

12

Exemple

CC=gcc

CFLAGS=-W -Wall -ansi -pedantic

LDFLAGS=

EXEC=hello

all: $(EXEC)

hello: hello.o main.o

$(CC) -o hello hello.o main.o $(LDFLAGS)

hello.o: hello.c

$(CC) -o hello.o -c hello.c $(CFLAGS)

Publicité

main.o: main.c hello.h

$(CC) -o main.o -c main.c $(CFLAGS)

clean:

rm -rf *.o

mrproper: clean

18/01/18

rm -rf $(EXEC)

13

Exemple

● -W -Wall : Valider les avertissements (warnings)

décrits en arguments. Il en existe une multitude.

mais l'option la plus couramment utilisée est

-Wall , pour activer tous les avertissements.

● -pedantic : Le compilateur fournit des

avertissements encore plus rigoureux qu'avec

-Wall, principalement orientés sur la portabilité du

code

● -ansi : Compatible avec la norme C Ansi

18/01/18

14

Exemple

● Pour compiler le projet

– $make

● Pour supprimer tout les fichiers intermédiaires.

– $make clean

● Pour supprimer tout ce qui peut être régénéré et

permet une reconstruction complète du projet.

– $make mrproper

18/01/18

15

The END

18/01/18

16