Answers:
您可以通过几个选项从makefile外部设置变量:
从环境 -每个环境变量都转换为具有相同名称和值的makefile变量。
您可能还希望将-e
option(aka --environments-override
)设置为on,并且您的环境变量将覆盖在makefile中进行的赋值(除非这些赋值本身使用override
指令。但是,不建议这样做,并且使用?=
赋值(条件变量)会更好,更灵活赋值运算符,它仅在尚未定义变量的情况下才有效):
FOO?=default_value_if_not_set_in_environment
请注意,某些变量不是从环境继承的:
MAKE
是从脚本名称获得的SHELL
是在makefile中设置的,或者默认为/bin/sh
(rationale:命令在makefile中指定,并且它们是特定于shell的)。从命令行 - make
可以将变量分配作为其命令行的一部分,并与目标混合:
make target FOO=bar
但是,除非在赋值中使用指令,否则将忽略makefile中对FOO
变量的所有赋值。(效果与环境变量的选项相同)。override
-e
从父Make导出 -如果从Makefile调用Make,通常不应显式编写如下变量分配:
# Don't do this!
target:
$(MAKE) -C target CC=$(CC) CFLAGS=$(CFLAGS)
相反,更好的解决方案可能是导出这些变量。导出变量会使它进入每次Shell调用的环境,并且从这些命令进行的Make调用将如上所述选择这些环境变量。
# Do like this
CFLAGS=-g
export CFLAGS
target:
$(MAKE) -C target
您也可以使用不带参数的方式导出所有变量export
。
export PROJECT_MAKE_ARGS = CC=$(CC) CFLAGS=$(CFLAGS)
为as并将其传递make -C folder $(PROJECT_MAKE_FLAGS)
。如果有办法告诉库的makefile忽略环境,那将是理想的选择(与-e相反)。
make target FOO=bar
make FOO=bar target
?
included
主makefile中的makefile?
假设您有一个这样的makefile:
action:
echo argument is $(argument)
然后,您将其称为 make action argument=something
从手册:
make中的变量可以来自运行make的环境。make看到的每个环境变量在启动时都会转换为具有相同名称和值的make变量。但是,makefile中的显式分配或使用命令参数会覆盖环境。
因此,您可以(从bash中)进行操作:
FOOBAR=1 make
FOOBAR
在您的Makefile中产生一个变量。
Stallman和McGrath所著的GNU Make书中还包含一个未在此处引用的选项(请参阅http://www.chemie.fu-berlin.de/chemnet/use/info/make/make_7.html)。它提供了示例:
archive.a: ...
ifneq (,$(findstring t,$(MAKEFLAGS)))
+touch archive.a
+ranlib -t archive.a
else
ranlib archive.a
endif
它涉及验证给定参数是否出现在中MAKEFLAGS
。例如,..假设您正在研究c ++ 11中的线程,并且已将研究分为多个文件(class01
,...,classNM
),并且您希望:然后全部编译并单独运行或一次编译一个文件。时间并运行(如果指定了标志-r
,例如)。因此,您可以提出以下建议Makefile
:
CXX=clang++-3.5
CXXFLAGS = -Wall -Werror -std=c++11
LDLIBS = -lpthread
SOURCES = class01 class02 class03
%: %.cxx
$(CXX) $(CXXFLAGS) -o $@.out $^ $(LDLIBS)
ifneq (,$(findstring r, $(MAKEFLAGS)))
./$@.out
endif
all: $(SOURCES)
.PHONY: clean
clean:
find . -name "*.out" -delete
有了它,您将:
make -r class02
;make
或make all
;make -r
(假设它们都包含某种肯定的东西,而您只想测试它们)
make A='"as df"'