[英]Is there a way to force rebuilding a target (make -B) without rebuilding its dependencies?
GNU Make has -B
option that forces make
to ignore existing targets. GNU Make有
-B
选项,强制make
忽略现有目标。 It allows to rebuild a target, but it also rebuilds all the dependency tree of the target. 它允许重建目标,但它也会重建目标的所有依赖关系树。 I wonder is there a way to force rebuilding a target without rebuilding its dependencies (using GNU Make options, settings in Makefile, compatible
make
-like software, etc.)? 我想知道有没有办法强制重建目标而不重建其依赖项(使用GNU Make选项,Makefile中的设置,兼容的
make
like软件等)?
Illustration of the problem: 问题的插图:
$ mkdir test; cd test
$ unexpand -t4 >Makefile <<EOF
huge:
@echo "rebuilding huge"; date >huge
small: huge
@echo "rebuilding small"; sh -c 'cat huge; date' >small
EOF
$ make small
rebuilding huge
rebuilding small
$ ls
huge Makefile small
$ make small
make: 'small' is up to date.
$ make -B small
rebuilding huge # how to get rid of this line?
rebuilding small
$ make --version | head -n3
GNU Make 4.0
Built for x86_64-pc-linux-gnu
Copyright (C) 1988-2013 Free Software Foundation, Inc.
Of course one can rm small; make small
当然一个人可以
rm small; make small
rm small; make small
, but is there a built-in way? rm small; make small
,但有内置的方式吗?
One way is to use the -o
option for all targets you don't want to be remade: 一种方法是对您不想重新制作的所有目标使用
-o
选项:
-o FILE, --old-file=FILE, --assume-old=FILE Consider FILE to be very old and don't remake it.
EDIT 编辑
I think you're misreading the documentation for -B
; 我认为你误读了
-B
的文档; it says: 它说:
-B, --always-make Unconditionally make all targets.
Note, the all targets here; 注意,这里的所有目标 ;
huge
is certainly a target, and so if you use -B
it will be remade. huge
的肯定是一个目标,所以如果你使用-B
它将被重新制作。
However, I also misread your question a bit. 但是,我也误解了你的问题。 I thought you wanted to rebuild
small
without rebuilding huge
even though huge
is new, but you're trying to get small
to be rebuilt even though huge
has not changed, right? 我认为你想要重建
small
而不重建huge
即使huge
是新的,但你正试图变small
,即使huge
没有改变,重建,对吧?
You definitely don't want to use -B
. 你绝对不想使用
-B
。 That option is not at all what you are looking for. 那个选项根本不是你想要的。
Normally people would do that by deleting small
: 通常人们会通过删除
small
来做到这small
:
rm -f small
make small
It might be useful to have an option that forced a given target to be recreated, but that option doesn't exist. 有一个强制重新创建给定目标的选项可能很有用,但该选项不存在。
You could use -W huge
, but again this means you need to know the name of the prerequisite not just the target you want built. 您可以使用
-W huge
,但这意味着您需要知道先决条件的名称,而不仅仅是您想要构建的目标。
Will this help: 这有用吗:
touch huge; make small
? ?
File under rather nasty hack: 在相当讨厌的黑客文件下:
huge:
@echo "rebuilding huge"; date >huge
small: $(if $(filter just,${MAKECMDGOALS}),huge)
@echo "rebuilding small"; sh -c 'cat huge; date' >small
.PHONY: just
just: ;
Now you can 现在你可以
$ make -B just small
Well, so far I'm using this partial solution: 好吧,到目前为止我正在使用这个部分解决方案:
$ cat >~/bin/remake <<'EOF'
#!/bin/sh
# http://stackoverflow.com/questions/42139227
for f in "$@"; do
if [ -f "$f" ]; then
# Make the file very old; it's safer than removing.
touch --date=@0 "$f"
fi
done
make "$@"
EOF
$ chmod u+x ~/bin/remake
$ # PATH="$HOME/bin:$PATH" in .bashrc
$ remake --debug=b small
GNU Make 4.0
Built for x86_64-pc-linux-gnu
Copyright (C) 1988-2013 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.
Reading makefiles...
Updating goal targets....
Prerequisite 'huge' is newer than target 'small'.
Must remake target 'small'.
rebuilding small
I use something like this: 我使用这样的东西:
remake()
{
for f in "$@"
do
[ -f "$f" ] && rm -f "$f"
done
make "$@"
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.