Aller au contenu

GNU Make

Un article de Wikipédia, l'encyclopédie libre.
GNU Make
Description de l'image Heckert GNU white.svg.

Informations
Créateur Richard Stallman et Roland McGrath (d)Voir et modifier les données sur Wikidata
Développé par Projet GNU
Première version Voir et modifier les données sur Wikidata
Dernière version 4.4.1 ()[1]Voir et modifier les données sur Wikidata
Dépôt git.savannah.gnu.org/cgit/make.gitVoir et modifier les données sur Wikidata
Écrit en CVoir et modifier les données sur Wikidata
Système d'exploitation GNU/Linux, BSD, macOS et Microsoft WindowsVoir et modifier les données sur Wikidata
Environnement GNU/Linux
Type Moteur de production
Licence GPLv3
Site web www.gnu.org/s/make/

GNU make est la variante GNU du moteur de production make. Gmake est le fruit de la collaboration entre Richard Stallman et Roland McGrath.

Spécificités

[modifier | modifier le code]

Certaines des spécificités citées ci-après peuvent ne pas être strictement propres à GNU make dans la mesure où elles peuvent avoir été héritées d'autre variantes ou encore imitées par d'autres variantes mais également avoir été inventées indépendamment de part et d'autre.

Il n'est pas ici question de se substituer au (en)manuel utilisateur mais de mettre en évidence les éléments les plus remarquables.

Valeur des variables

[modifier | modifier le code]

Alors que la valeur d'une variable est traditionnellement traitée comme une macro de manière récursive au moment de son utilisation, GNU make permet la définition de variables dont la valeur est fixée au moment de leur définition.

Exemple traditionnel :

    titi = $(tata)
    tata = $(toto)
    toto = salut
    
    all:;echo $(titi)

affichera "salut" après que titi aura été évalué en tata à son tour évalué en toto finalement évalué en salut[2].

Cette première saveur est la seule connue des autres variantes de make. Celle-ci a des avantages, elle permet en particulier que la valeur finale effective ne puisse être déterminée qu'en dernière instance. Elle offre également une certaine souplesse dans l'ordre des déclarations, ainsi dans l'exemple ci-dessus, le résultat est indépendant de l'ordre des trois premières déclarations.

Cette première saveur a par contre deux désavantages. Le moindre est que les variables sont systématiquement réévaluées à chacune de leur utilisation (même quand leur valeur reste constante) ce qui constitue une charge inutile dans ce cas précis. L'autre est que, dans le cas général, elle ne permet pas que sa redéfinition puisse se faire comme dans l'exemple ci-après[3] :

    titi = jour
    toto = bon
    titi = $(toto)${titi}

Dans ce cas, la troisième ligne conduit à une définition récursive de titi qui sera rejetée comme erreur par GNU make.

La seconde saveur possible avec GNU make est illustrée par l'exemple ci-après[3] :

    x := titi
    y := $(x) tata
    x := toto

est équivalent à :

    y := titi tata
    x := toto

En d'autres termes, cette seconde saveur confère aux variables ainsi définies un comportement identique à celui des variables de la plupart des autres langages de programmation tel que le Langage C par exemple.

Règles génériques

[modifier | modifier le code]

Make permet de définir des règles explicites et implicites ou génériques[4].

  • Dans une règle explicite les fichiers sources et cibles sont explicitement nommés soit sous directement forme littérale constante soit indirectement par l'intermédiaire de variables ou encore, dans le cas de GNU make par des appels de fonctions.
  • Dans une règle implicite, source et cibles sont décrites par des expressions régulières simplifiées. Quand, à défaut d'être décrite par une règle explicite, le nom d'une cible et de sa source potentielle sont conformes aux expressions régulières d'une règle générique, alors cette dernière peut s'appliquer.

Dans la plupart des variantes de make de telles expressions se réduisent à des simples couples de suffixes. Quand pour un nom de fichier cible il existe fichier source de même racine et qu'il existe un règle implicite liant le suffixe de la cible à celui du source alors la règle peut s'appliquer. Exemple :

       .c.o:
            $(CC) -c $(CFLAGS) $(CPPFLAGS) -o $@ $<

Décrit comment de manière implicite tout fichier de suffixe ".o" peut être produit à partir du fichier de suffixe ".c"

GNU make permet des expressions régulières un peu plus complexe et dont la syntaxe est analogue à celle des règles explicites. Exemple :

    %.o: %.c toto.h
            $(CC) -c $(CFLAGS) $(CPPFLAGS) -o $@ $<

On remarquera dans cet exemple que la règle génériques ainsi définie ne se limite pas à lier les suffixes ".o" et ".c" mais permet en outre d'imposer ou spécifier (selon le point de vue) une dépendance supplémentaire à un fichier particulier : "toto.h" (dans l'exemple). Dans cette syntaxe c'est le caractère "%" qui localise le motif (ou encore pattern) commun entre source et cible.

Cette syntaxe permet de ne pas se limiter au seul suffixe. Ainsi dans l'exemple :

    f%.o: g%.c 
            $(CC) -c $(CFLAGS) $(CPPFLAGS) -o $@ $<

on impose par ailleurs que la règle générique ne s'appliquera qu'à des cible de suffixe ".o" dont le nom de fichier commence par "f" et pour un source de suffixe ".c" dont le nom de fichier commence par "g" et partageant le même motif "%". Ainsi seront concernée par la règle générique définie plus haut les couples :

     fifi.o gifi.c
     foto.o goto.c

mais pas les couples :

     fifi.o fifi.c
     goto.o goto.c

GNU make offre un jeu étendu de fonctions pouvant être utilisées en toute place où on pourrait trouver une référence de variable. La syntaxe d'appel à une fonction, très similaire à celle d'une référence de variable, est de la forme générale :

       ${fonction arguments}

Parmi les fonctions disponibles on peut identifier les catégories suivantes :

  • fonctions généralistes de traitement de chaînes de caractères : substitutions, extractions, recherches, filtrages, tris, etc.
  • fonctions dédiées à la manipulation des noms de fichiers : extractions du nom de base, du suffixe, du chemin, exploitation d'expressions régulières de type "shell", de construction, de normalisation des noms(forme canonique), etc.
  • fonction permettant de construire des expressions conditionnelles simples (si, ou, et) dans le contexte de l'utilisation des fonctions[5].
  • la fonction $(foreach nom, liste, texte) qui permet de construire des listes en répétant texte pour chaque mot présent dans liste en substituant celui-ci dans chaque occurrence de référence à nom présent dans texte.
  • la fonction $(call variable, param, param, ...) qui permet d'invoquer n'importe quelle fonction construite par l'utilisateur (voir plus loin) et dont la définition est donnée par variable.
  • la fonction $(shell texte) qui permet d'exécuter une fonction en dehors de l'environnement d'accueil (commandes disponibles dans l'environnement d'accueil) et usuellement utilisé pour affecter à une variable une information sur l'environnement extérieur à make (récupérer une date, le nom de la machine, de l'utilisateur, etc.).
  • diverses fonctions permettant de connaître l'état (définie ou non), l'origine de sa définition (dans le makefile, la ligne de commande, une variable d'environnement, etc.), la saveur, la portée de toute chaîne de caractères susceptible d'identifier une variable.
  • des fonctions permettant de contrôler l'exécution en levant des erreurs, des avertissements ou simplement en affichant des messages.

GNU make permet également à l'utilisateur de définir ses propres fonctions en factorisant via la définition d'une variable (le nom de la fonction) dont la valeur est combinaison d'autres fonctions et variables (formelles ou réelles).

Le support de Guile est assuré depuis la version 4.0[6]. La première brique logicielle à l’exploiter sera probablement Guix, un gestionnaire de paquets purement fonctionnel conçu pour GNU.

Notes et références

[modifier | modifier le code]
  1. « GNU Make 4.4.1 released! »
  2. salut n'étant pas lui-même défini comme une variable il est traité comme une chaîne de caractères constante
  3. a et b Il s'agit bien sûr ici juste d'un cas d'école
  4. Les règles implicites sont juste des règles génériques prédéfinies
  5. À ne pas confondre avec le code conditionnel qui permet d'exclure ou inclure de manière conditionnelle la prise en compte de certaines parties du makefile
  6. (en) « GNU Make 4.0 Brings New Features, Extends With Guile », sur phoronix.com, (consulté le ) ;

Liens externes

[modifier | modifier le code]