强制GNU-make使用符号链接目标的修改时间,而不是源的修改时间

问题描述 投票:2回答:1

我遇到GNU make 3.81中修改时间的问题。

我的Makefile使用从远程服务器安装的数据,由于某些原因我不知道,它已经将文件的修改时间设置为遥远的未来(进入下个世纪)。

Makefile首先在本地目录中创建一个“从未来”远程文件的符号链接,然后基于该文件运行几个脚本,这些脚本都生成一些输出文件。

现在,当我想在重叠之后重新运行“make all”以获取所有输出文件时,它将不会使用它生成的最新输出文件重新启动(假设从脚本编号3开始),而是重新生成所有内容从一开始,因为它注意到第一个文件(我将来自未来的符号链接文件的那个文件)更新。

是否有一个选项告诉make接受符号链接本身的修改时间,而不是符号链接目标的修改时间?

这是一个重新生成问题的最小工作示例:

设置文件夹和文件:

mkdir symlinkmake
cd symlinkmake
echo $PWD > futurefile.txt
# set file modification time to the future
touch -t 212111111111 futurefile.txt

Makefile的内容:

all: symlink.txt first_output.txt second_output.txt

symlink.txt:
    ln -s futurefile.txt symlink.txt

first_output.txt: symlink.txt
    cut -f1 -d"/" symlink.txt > first_output.txt

second_output.txt: first_output.txt
    wc first_output.txt > second_output.txt

现在运行make all并删除第二个输出文件。然后重新运行make。由于第一个输出文件已存在,因此只需要生成第二个文件。但由于futurefile.txt比任何其他文件更新,因此第一个输出文件也将生成:

make all
rm second_output.txt
make all

在我的机器上,输出如下所示:

$ ls
Makefile        futurefile.txt  symlink.txt
$ make all
make: Warning: File `symlink.txt' has modification time 3.3e+09 s in the future
cut -f1 -d"/" symlink.txt > first_output.txt
wc first_output.txt > second_output.txt
make: warning:  Clock skew detected.  Your build may be incomplete.
$ rm second_output.txt
$ make all
make: Warning: File `symlink.txt' has modification time 3.3e+09 s in the future
cut -f1 -d"/" symlink.txt > first_output.txt
wc first_output.txt > second_output.txt
make: warning:  Clock skew detected.  Your build may be incomplete.
unix makefile gnu-make symlink
1个回答
4
投票

--check-symlink-times make option但是:

在支持符号链接的系统上,除了这些链接引用的文件上的时间戳之外,此选项还会使make考虑任何符号链接上的时间戳。提供此选项时,文件和符号链接中的最新时间戳将被视为此目标文件的修改时间。

这不是你想要的只考虑链接的时间戳。由于您无法解决日期/时间问题,我只能想象一下2个解决方案

  1. order-only prerequisites(OOP): .PHONY: all all: first_output.txt second_output.txt | symlink.txt symlink.txt: ln -s futurefile.txt $@ first_output.txt: | symlink.txt cut -f1 -d"/" $| > $@ second_output.txt: first_output.txt wc $< > $@ 作为OOP制作的symlink.txt只会考虑它的存在,而不是它的时间戳。换句话说,make将构建它,并且(重新)构建依赖于它的所有目标,只有它缺失。 注意:我还在任何可能的地方使用过automatic variables。它们很方便,不易出错,并且经常允许对规则进行分解。 缺点:这是一个快速而肮脏的黑客而不是真正的解决方案。实际上,如果链接引用的文件发生更改,则不会重建其他目标: $ ls -al Sep 14 14:55 Makefile Dec 1 2018 futurefile.txt $ make ln -s futurefile.txt symlink.txt cut -f1 -d"/" symlink.txt > first_output.txt wc first_output.txt > second_output.txt $ ls -al Sep 14 14:55 Makefile Sep 14 15:05 first_output.txt Dec 1 2018 futurefile.txt Sep 14 15:05 second_output.txt Sep 14 15:05 symlink.txt -> futurefile.txt $ make make: Warning: File 'symlink.txt' has modification time 6688452 s in the future make: Nothing to be done for 'all'. make: warning: Clock skew detected. Your build may be incomplete. $ touch --date=2018-12-02 futurefile.txt $ ls -al futurefile.txt $ make make: Warning: File 'symlink.txt' has modification time 6774852 s in the future make: Nothing to be done for 'all'. make: warning: Clock skew detected. Your build may be incomplete.
  2. 为了减轻第一个解决方案的缺点,您将在构建目标时用远程服务器的日期/时间替换本地主机的日期/时间。偶然,touch命令有一个很好的--reference选项,强制文件的时间戳是另一个文件的时间戳: .PHONY: all all: first_output.txt second_output.txt first_output.txt: futurefile.txt cut -f1 -d"/" $< > $@ touch --reference=$< $@ second_output.txt: first_output.txt wc $< > $@ touch --reference=$< $@ 缺点:将来有两个文件(first_output.txtsecond_output.txt),而不是一个符号链接: $ ls -al Sep 14 14:55 Makefile Dec 1 2018 futurefile.txt $ make make: Warning: File 'futurefile.txt' has modification time 6688320 s in the future cut -f1 -d"/" futurefile.txt > first_output.txt touch --reference=futurefile.txt first_output.txt wc first_output.txt > second_output.txt touch --reference=first_output.txt second_output.txt make: warning: Clock skew detected. Your build may be incomplete. $ ls -al Sep 14 14:55 Makefile Dec 1 2018 first_output.txt Dec 1 2018 futurefile.txt Dec 1 2018 second_output.txt $ make make: Warning: File 'first_output.txt' has modification time 6688320 s in the future make: Nothing to be done for 'all'. make: warning: Clock skew detected. Your build may be incomplete. $ touch --date=2018-12-02 futurefile.txt $ ls -al futurefile.txt $ make make: Warning: File 'first_output.txt' has modification time 6688320 s in the future cut -f1 -d"/" futurefile.txt > first_output.txt touch --reference=futurefile.txt first_output.txt wc first_output.txt > second_output.txt touch --reference=first_output.txt second_output.txt make: warning: Clock skew detected. Your build may be incomplete.
© www.soinside.com 2019 - 2024. All rights reserved.