每个规则的已用时间

我有这个bash代码:

(在脚本的开始:)

function timer() { if [[ $# -eq 0 ]]; then echo $(date '+%s') else local stime=$1 etime=$(date '+%s') if [[ -z "$stime" ]]; then stime=$etime; fi dt=$((etime - stime)) ds=$((dt % 60)) dm=$(((dt / 60) % 60)) dh=$((dt / 3600)) printf '%d:%02d:%02d' $dh $dm $ds fi } t=$(timer) 

(并在脚本的末尾:)

 printf 'Elapsed time: %s\n' $(timer $t) 

来计算脚本经过的总时间。 此代码在bash(shell)脚本中正常工作。 所以,我想把这个代码放在每个规则的makefile中。

我怎样才能把这个函数在Makefile中? 怎么能在每个规则call'em?

我做了这样的事情:

 define TIME stime=$(1) etime=$(date '+%s') dt=$((etime - stime)) \ ds=$((dt % 60)) \ ... endef 

并在每个规则:

 rule1: dep1 dep2 dep3 ...SOME STUFF @$(call TIME, starttime) rule2: depx depD rule1 ...SOME STUFF @$(call TIME, starttime) 

但math运算不起作用。 我尝试了很多东西,但是我做不到

麻烦的是,在你的bash脚本中,变量t从开始(工作之前)到结束(当它可以从结束时间减去时)存活。 在Make配方中,每行都有自己的shell,因此在早期行中设置的shell变量在后面的行中将不可用。

你可以把一个配方的所有命令串在一起,这样你就可以在开始时设置t并在最后使用它,但是这很笨拙。 我建议你写一个文件,也许rule1_time ,这样两个调用timer不需要一个公共变量。 呵呵,不要试图在命令里面使用call

 STIME = date '+%s' > $@_time ETIME = read st < $@_time ; echo $$((`date '+%s'`-$$st)) all: $(STIME) do stuff $(ETIME) 

编辑:
我写了上面的代码作为概念证明; 我只是为了澄清,而不是细化。 如果我正确理解你的评论,你现在想知道如何将时间分解成几小时,几分钟和几秒钟,而不用从每个规则调用几个函数。 有几种方法可以做到,这可能是最干净的:

 ETIME = @read st < $@_time ; st=$$((`date '+%s'`-$$st-68400)) ; echo Elapsed time: `date -r $$st '+%H:%M:%S'` 

如果您正在尝试获取构建步骤的时间信息,更好的解决方案是使用更智能的构建。 Electric Cloud的ElectricMake可以生成构建日志的XML标记版本,称为注释文件 ,其中包含构建调用的每个命令的确切时间数据,以及一系列其他信息,如确切的命令行使用(即使您使用@前缀)和每个命令使用的环境变量。

您可以免费试用SparkBuild ,一个免费版本的ElectricMake。

你可以使用时间:

所有:
     @@时间( \
         rsync -az $ {src1} $ {dest1} \
         && rsync -az $ {src2} $ {dest2} \
         ##等
     )

在这里不能使用制表符,但记住makefile只使用制表符(因为POSIX要求)。