Comment changer les valeurs par défaut de variables comme CC dans Makefile

(GNU) make utilise plusieurs variables comme:

  • CC -- compilateur C, par défaut cc
  • CFLAGS -- drapeaux pour le compilateur C, par défaut vide

je voudrais spécifier mes propres valeurs par défaut de certains d'entre eux dans mon Makefile. Dans l'exemple ci-dessous j'ai utilisé le conditionnel opérateur d'affectation ?= pour être capable de modifier mes valeurs par défaut lors de l'exécution make:

CFLAGS ?= CFLAGS_my_default
CC ?= CC_my_default

print:
    echo CC=$(CC) CFLAGS=$(CFLAGS)

Malheureusement cela ne change pas la valeur de l' CC variable car la valeur initiale par défaut y reste. CFLAGS sont définis par mon affectation car la variable était vide à l'origine:

$ make print
echo CC=cc CFLAGS=CFLAGS_my_default
CC=cc CFLAGS=CFLAGS_my_default

Substituant à partir de variables d'environnement fonctionne comme prévu:

$ CC=CC_from_env CFLAGS=CFLAGS_from_env make print
echo CC=CC_from_env CFLAGS=CFLAGS_from_env
CC=CC_from_env CFLAGS=CFLAGS_from_env

Comment puis-je changer les valeurs par défaut des variables tout en étant capable de les surpasser lors de l'invocation <!--8?

14
demandé sur pabouk 2013-08-02 05:29:58

2 réponses

j'ai utilisé cette Makefile exécuter quelques tests avec GNU Make et vérifier l' origine et la valeur par défaut de certaines variables:

define whatisit
$(info $(1) origin is ($(origin $(1))) and value is ($($(1))))
endef

$(call whatisit,CC)
$(call whatisit,CFLAGS)

Voici les résultats:

$ make
CC origin is (default) and value is (cc)
CFLAGS origin is (undefined) and value is ()
$ # Environment
$ CC=clang CFLAGS=-Wall make
CC origin is (environment) and value is (clang)
CFLAGS origin is (environment) and value is (-Wall)
$ # Command line
$ make CC=clang CFLAGS=-Wall
CC origin is (command line) and value is (clang)
CFLAGS origin is (command line) and value is (-Wall)

Comme vous pouvez le voir il y a deux types de variables. Ces types sont définis dans le manuel.

Le premier ensemble de variables (AR,AS,CC,...)default valeurs. Le deuxième ensemble de variables (ARFLAGS, ASFLAGS,CFLAGS,...) sont par défaut à une chaîne vide (i.e. undefined).

par défaut, ils peuvent être supplantés par environnement ou ligne de commande.


définir la valeur par défaut pour le undefined variables

pour le undefined variables (et aussi d'autres variables utilisateur) vous avez juste à utiliser le ?= opérateur pour définir une valeur par défaut qui peut être outrepassée par environnement ou ligne de commande.

CFLAGS ?= -Wall -Wextra -Werror

Définir la valeur par défaut pour l' default variables

La meilleure façon de changer la valeur par défaut pour l' default variables est de vérifier leur origine et de modifier la valeur uniquement lorsque cela est nécessaire.

ifeq ($(origin CC),default)
CC = gcc
endif

Conclusion

Makefile:

ifeq ($(origin CC),default)
CC  = gcc
endif
CFLAGS  ?= -Wall -Wextra -Werror

define whatisit
$(info $(1) origin is ($(origin $(1))) and value is ($($(1))))
endef

$(call whatisit,CC)
$(call whatisit,CFLAGS)

Le résultat:

$ make
CC origin is (file) and value is (gcc)
CFLAGS origin is (file) and value is (-Wall -Wextra -Werror)
$ # Environment
$ CC=clang CFLAGS=-Wall make
CC origin is (environment) and value is (clang)
CFLAGS origin is (environment) and value is (-Wall)
$ # Command line
$ make CC=clang CFLAGS=-Wall
CC origin is (command line) and value is (clang)
CFLAGS origin is (command line) and value is (-Wall)

Facultatif

Vous pouvez utiliser le MAKEFLAGS variable pour désactiver les règles implicites intégrées et les paramètres variables intégrés. De cette façon:

MAKEFLAGS += -rR

cela nettoiera beaucoup de paramètres par défaut (vous pouvez le vérifier en utilisant make -p). Mais l' default variables (comme CC) auront toujours une valeur par défaut.

5
répondu jml 2017-03-22 17:39:44

il est possible d'utiliser l'assignation non-conditionnelle:

CFLAGS ?= CFLAGS_my_default
CC = CC_my_default

print:
    echo CC=$(CC) CFLAGS=$(CFLAGS)

mais sans condition définir les variables ne peuvent pas être remplacés à partir de variables d'environnement:

$ CC=CC_from_env CFLAGS=CFLAGS_from_env make print
echo CC=CC_my_default CFLAGS=CFLAGS_from_env
CC=CC_my_default CFLAGS=CFLAGS_from_env

attendez, il y a une autre façon de définir la variable en invoquant make! - à partir d'arguments de ligne de commande:

$ make print CC=CC_from_cmdline CFLAGS=CFLAGS_from_cmdline
echo CC=CC_from_cmdline CFLAGS=CFLAGS_from_cmdline
CC=CC_from_cmdline CFLAGS=CFLAGS_from_cmdline

de cette façon, les variables non-conditionnellement définies sont dépassées aussi. Cette méthode fonctionne même avec récursive utilisation de make variables spécifié sur la ligne de commande sont automatiquement transférés sur le nouveau make processus.

une autre méthode consiste à activer la suppression des variables inconditionnelles par les variables d'environnement en utilisant la commande switch -e:

$ CC=CC_from_env CFLAGS=CFLAGS_from_env make -e print
echo CC=CC_from_env CFLAGS=CFLAGS_from_env
CC=CC_from_env CFLAGS=CFLAGS_from_env
11
répondu pabouk 2013-08-02 17:17:03