这是我的Makefile:
.PHONY: test%
test1:
# jobserver is UNavailable
make -C sub
test2:
# jobserver is available, ok
+make -C sub
test3:
# jobserver is available, ok
$(MAKE) -C sub
test4:
# jobserver is available, ok
+$(MAKE) -C sub
sub
是包含另一个Makefile (Sub)的子目录.
当我运行test1
规则时:
$ make -j8 test1
make -C sub
make[1]: warning: jobserver unavailable: using -j1. Add '+' to parent make rule.
我收到警告,j观察者不可用,sub/Makefile
实际上是在单个线程中运行的(就像-j1
一样)。
他们说我应该添加+
,所以我运行一个test2
目标,在make
命令之前包含+
。现在我没有看到警告,sub/Makefile
实际上是并行运行的。但是根据这个答案,+
标志不是用于并行运行,而是用于强制运行命令,即使make
是使用-n
、-t
、-q
标志运行的。但是为什么+
会启用j观察者呢?
当我运行不使用test3
但使用$(MAKE)
运行sub/Makefile
的目标时,它也不会给出j观察者警告(并行执行工作)。那么,make
和$(MAKE)
有什么区别呢?我认为这只是为了允许用用户定义的make替换默认make。当我不覆盖MAKE
变量时,我看到的make
命令与在test1
目标中看到的相同。但是,为什么$(MAKE)
启用j观察者而make
不启用呢?
运行test4
目标也不会发出j观察者警告(并行工作)。
发布于 2020-03-16 12:51:43
对于这个错误,GNU手册有很好的解释。要点是:'make‘不会将j观察者的信息传递给被调用的进程,除非它确定被调用的进程也是'make’。
警告:j观察者不可用:使用-j1。将`+‘添加到父级规则中。 为了使进程进行通信,父进程将向子进程传递信息。因为如果子进程实际上不是make,那么这可能会导致问题,因此父进程只有在它认为子进程是make时才会这样做。父级使用常规算法来确定此值(请参见MAKE变量是如何工作的)。如果makefile的构造使得父进程不知道子进程是make进程,那么子进程将只接收所需信息的一部分。在这种情况下,子程序将生成此警告消息,并按顺序进行其构建。
错误描述中引用的MAKE变量是如何工作的节指定了两种方法来告诉“make”调用的进程是“make”的另一个实例:使用$(MAKE)
或+
。它指出:
$(MAKE)
变量。递归make命令应该始终使用变量MAKE,而不是显式命令名‘make’,如下所示:
子系统: cd && $(MAKE)$(MAKE)
并在菜谱中调用“make”的行之前放置一个+
具有相同的效果。使用MAKE变量的效果与在菜谱行开头使用“+”字符的效果相同。MAKE
时才会发生魔术。如果不是这样,请使用+
。只有当MAKE变量直接出现在配方中时,才启用此特殊功能:如果通过扩展另一个变量引用MAKE变量,则不适用该特性。在后一种情况下,您必须使用“+”令牌来获得这些特殊效果。https://stackoverflow.com/questions/60702726
复制相似问题