2013-04-08 122 views
4

我正在学习makefile。我在makefile中理解eval的用法有问题。如何在Makefile中使用eval

这是我的Makefile:

testt: 
    @R=5 
    $(eval $(echo $R)) 

当我运行化妆testt,则什么也不显示。 你能告诉我是什么原因吗?非常感谢。

回答

7

我不知道,stackoverflow是您在这里寻找信息的最佳位置。最好回答具体问题,但基于这个例子,你首先需要得到一些更基本的理解。

仅供参考,您测试中的第一行是设置外壳变量R。然后该行结束,从该shell调用中退出,现在您的变量设置将丢失。然后在下一行中通过引用$R访问使变量R。这从来没有设置任何地方,所以总是一个空的字符串。然后,您尝试将其赋予make函数$(echo ...),但make中没有这样的函数,因此也扩展为空字符串。然后将结果空字符串传递给$(eval ...)函数,然后评估空字符串会产生另一个空字符串,然后将该字符串作为要运行的命令提供给shell,该命令不执行任何操作。

如果你想问一个具体的问题(“我该怎么做XYZ?”),那么我们可以给出一个答案...但是这需要GNU make手册的重要部分来帮助达到这个水平。你也可以在[email protected]邮件列表上询问。

+0

感谢您的快速响应。我很抱歉我的新手问题,但我不明白,原因是空的变量。我试过了: testt: $(eval $(echo abc)) 但是再一次,没有任何显示。 – AlexTP 2013-04-08 18:45:27

+0

@PatrickDiwel:'echo'是一个shell命令,但你正在试图评估它,就好像它是一个Make函数。 – Beta 2013-04-08 20:03:39

+2

同样,我认为stackoverflow不是这个级别问题的正确位置。我强烈建议您将您的问题重定向到[email protected]邮件列表:他们有更多的经验来提供基本的理解。 make中的$(eval ...)函数是一个非常高级的主题。如果你不清楚shell变量和make变量之间的区别,shell命令和make函数,以及它们在什么时候以及如何进行交互时使用,那么理解'$(eval ...)'很简单不现实。 – MadScientist 2013-04-08 20:15:17

5

当make在您的makefile中读取时,它将testt的shell命令块作为单个递归扩展变量存储。没有什么不幸发生了。

读完你的makefile后,现在决定做什么。 testt是第一个目标,所以它有一个去。您的文件系统中没有名为testt的文件,因此请确定它必须运行shell命令块。

在这一点上,它试图扩大它早先松动的变量。它始于

@R=5 
$(eval $(echo $R)) 

首先是扩大$R。扩展为空,剩余使用

@R=5 
$(eval $(echo)) 

现在,它扩大$(echo)。此变量不存在任何,并已就

@R=5 
$(eval) 

制作不知道$(eval ...)了,但它的输出始终是空的。所以现在制作了

@R=5 

扩展完成后,现在把每行分别依次传递给shell的新调用,检查每个的返回码。所以,外壳看到R=5。该命令(对shell变量的简单分配)完成而没有错误。由于前缀为@,Make不会将其回显为stdout。全做完了。

总是运行使--warn-undefined-variables

$ make --warn-undefined-variables 
Makefile:3: warning: undefined variable `R' 
Makefile:3: warning: undefined variable `echo ' 
make: Nothing to be done for `testt'. 

(注意在变量名的末尾额外的空间:`echo '(是的,你可以有变量名,其中包括空格))

哦,而我在这,$(eval ...)是真正有用的,但不要在shell命令中使用它。这很少有道理。

+0

这样一个很好的解释,但你仍然没有提供正确的表达。 – 2017-09-21 10:11:35

+0

@ Nik-Lz真的没有一个更正的表达式。正如我指出的那样,配方(通常)对于$(eval ...)来说是错误的地方。 OP的_make_片段显示了一些其他的误解。我只是想用_eval_来解决这个问题。 @MadScientist在他的回答中涵盖了其余部分。 – bobbogo 2017-09-22 15:48:56