我有一个make文件,它总是重新运行规则,尽管先决条件是最新的:
data.tar.bz2: data.tar
bzip2 --keep data.tar
#The following rule always runs the rule for its prerequisite even if it is up-to-date. Note that it doesn't matter whether regardless whether the bunzip2 directory exists or not. I suppose is has something to do with the dir/file naming of the rule but I haven't been able to decipher why.
bunzip2/data2.tar: data.tar.bz2
mkdir bunzip2 && cd bunzip2 && bzip2 -ckd ../data.tar.bz2 > data2.tar && cd ..
.PHONY: clean
clean:
rm -f data.tar.bz2
rm -Rf bunzip2
任何想法都赞赏。
答案 0 :(得分:1)
示例中缺少某些内容 - 但分析过程是相同的,无论如何:您可以使用make的调试功能来查看它使用的规则,例如,
make -d
答案 1 :(得分:1)
我想我知道这里发生了什么。
使用@Thomas Dickey建议尝试make -d
,它说文件data.tar.bz2
比data.tar
本身更新。这看起来很愚蠢,因为前者是从后来创造的。但是使用ls --full-time
显示bzip2存档似乎使用源文件的时间戳,但它也在第二个位置后截断它。就我而言,时间戳2015-03-12 09:32:02.452091888
被截断为2015-03-12 09:32:02.000000000
,这使得它看起来比源更新。 (截断我的意思是2015-03-12 13:10:29.681793152
转到2015-03-12 13:10:29.000000000
...即使在这种情况下也不会向上舍入)似乎bzip需要提高其时间戳的准确性。
lunzip
似乎还会截断时间戳,unxz
会保留原始时间戳,而gzip
会使用当前时间。换句话说,在使用压缩实用程序时要小心makefile,因为它们处理的方式不同。
答案 2 :(得分:1)
标准POSIX系统调用文件上设置的时间戳不支持亚秒级精度。为了使这些工具在文件上设置特定时间(他们尝试这样做以使压缩文件与原始文件具有相同的时间戳)并保持原始准确性,他们需要使用不同的系统调用;显然他们没有这样做。
你可以做些什么来改变你的规则:
data.tar.bz2: data.tar
bzip2 --keep data.tar && touch $@
以便将目标的时间戳设置为"现在"。
ETA 用于设置文件修改时间的传统系统调用是utime(),它仅以1秒为增量接受时间戳。较新版本的POSIX规范引入了utimensat(),允许纳秒时间戳设置。还有utimes()
允许微秒精度,但已被认为是#34;遗产"很长一段时间了。
如果当前最新版本的bzip2
中存在此行为,我认为这是一个值得向他们报告错误的错误。