GNU Make - 终端规则和关键字“null”
Posted
技术标签:
【中文标题】GNU Make - 终端规则和关键字“null”【英文标题】:GNU Make - terminal rules and keyword "null" 【发布时间】:2016-07-07 15:54:31 【问题描述】:背景
这和我的问题GNU make - transform every prerequisite into target (implicitly)有关
我发布了 这个 问题,因为它很有趣,并且它本身可能有用 - 理解 make
- 我不希望它迷失在“原始”问题中。
信息
我有一个文件Dummy.mk
:
%:: null
@:
null:
@:
我将其作为make all MAKEFILES=Dummy.mk
传递给我的make
。
当我将null
替换为saflkjsaflkjdsa
时,
%:: saflkjsaflkjdsa
@:
saflkjsaflkjdsa:
@:
构建的行为不同:规则从未执行。
原因是因为这是一个"terminal rule":
一种选择是通过定义将 match-anything 规则标记为终端 它带有一个双冒号。 当规则是终端时,它不适用 除非它的先决条件确实存在。可能的先决条件 用其他隐含规则制定的还不够好。换句话说,没有 允许超出最终规则的进一步链接。
由于saflkjsaflkjdsa
不存在,因此没有执行该规则。好的,我明白了。
但是当我使用关键字null
设置Dummy.mk
时
%:: null
@:
null:
@:
%::
规则确实执行,即它捕获所有目标、文件名等,给我:2: update target <item> due to: null
形式的输出,其中<item>
是make
读入的任何文件名或目标。
由于规则是使用null
而不是使用saflkjsaflkjdsa
执行,所以make
肯定会将null
检测为“现有”。
问题
但是为什么我仍然得到输出:5: target 'null' does not exist
?
这是因为null
存在但不同时存在的操作系统或外壳级别的特性吗?
环境
* Windows 8、64 位
* 制作 4.2.1(这里是make
的输出
# GNU Make 4.2.1
# Built for Windows32
# Copyright (C) 1988-2016 Free Software Foundation, Inc.
# License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
# This is free software: you are free to change and redistribute it.
# There is NO WARRANTY, to the extent permitted by law.
find_and_set_shell() path search set default_shell = C:/Users/User1/Desktop/A/QNX_SDK/host/win32/x86/usr/bin/sh.exe
...
* make
在内部使用的 Shell 是:
C:\Users\User1\Desktop\A\Project\bld\armle-v7\release\subProj>where sh
C:/Users/User1/Desktop/A/QNX_SDK/host/win32/x86/usr/bin/sh.exe
C:\Users\User1\Desktop\A\Project\bld\armle-v7\release\subProj>sh --help
GNU bash, version 3.1.17(1)-release-(i686-pc-msys)
Usage: sh [GNU long option] [option] ...
sh [GNU long option] [option] script-file ...
GNU long options:
--debug
--debugger
--dump-po-strings
--dump-strings
--help
--init-file
--login
--noediting
--noprofile
--norc
--posix
--protected
--rcfile
--restricted
--verbose
--version
--wordexp
Shell options:
-irsD or -c command or -O shopt_option (invocation only)
-abefhkmnptuvxBCHP or -o option
Type `sh -c "help set"' for more information about shell options.
Type `sh -c help' for more information about shell builtin commands.
Use the `bashbug' command to report bugs.
【问题讨论】:
【参考方案1】:这是因为 null 存在但不同时存在的操作系统或 shell 级别的特性吗?
由于您没有指定您使用的是哪个操作系统或外壳,我们无法说。我只能说我试图在我的 GNU/Linux 系统上复制您的问题,但不能:在我的系统上,无论哪种情况都没有构建目标(使用 null
或 saflkjsaflkjdsa
没有区别)
我怀疑您使用的是 Windows;我有一个模糊的回忆,null
在 Windows 上是特别的。但是,我不做 Windows,所以我不能肯定。
【讨论】:
我使用的是 Windows,但我使用的不是 CMD shell。 你使用的是用 MSVC 编译的 make 吗?还是明威?还是赛格温?请注意,您使用的 shell 大多是无关紧要的:make 不使用 shell 来确定哪些目标已过时。 shell 仅在 make 确定目标已过期并想要更新它时使用。在这里,您的问题是 make 正在检查该文件的存在并找到它,即使磁盘上没有名为null
的文件也是如此。 ISTR 在 Windows 上有一些特殊的设备,它们似乎总是存在但不是真实的文件。
在任何情况下,您都应该将此详细信息添加到您的问题中,并可能在您的问题中添加一个 windows 标签,也许一些 Windows 知识渊博的人会做出回应。
我更新了 shell 信息。我用 MSVC 编译了我的 make
。
为了使这个“设计模式”平台中立,是否可以用我知道总是存在的一些文件替换null
,比如$(firstword $(MAKEFILE_LIST))
?以上是关于GNU Make - 终端规则和关键字“null”的主要内容,如果未能解决你的问题,请参考以下文章