2010-10-14 22 views
123

这是我的Makefile:为什么认为目标是最新的?

REBAR=./rebar 
REBAR_COMPILE=$(REBAR) get-deps compile 

all: compile 

compile: 
    $(REBAR_COMPILE) 

test: 
    $(REBAR_COMPILE) skip_deps=true eunit 

clean: 
    -rm -rf deps ebin priv doc/* 

docs: 
    $(REBAR_COMPILE) doc 

ifeq ($(wildcard dialyzer/sqlite3.plt),) 
static: 
    $(REBAR_COMPILE) build_plt analyze 
else 
static: 
    $(REBAR_COMPILE) analyze 
endif 

我可以运行make compile多次,得到

[email protected]:~/workspace/gm-controller/lib/erlang-sqlite$ make compile 
./rebar get-deps compile 
==> erlang-sqlite (get-deps) 
==> erlang-sqlite (compile) 

然而,对于运行make test某种原因总是给人

[email protected]:~/workspace/gm-controller/lib/erlang-sqlite$ make test 
make: `test' is up to date. 

即使文件未编译。问题是,为什么?

运行相同的命令直接作用:

[email protected]:~/workspace/gm-controller/lib/erlang-sqlite$ ./rebar get-deps compile skip_deps=true eunit 
==> erlang-sqlite (get-deps) 
==> erlang-sqlite (compile) 
Compiled src/sqlite3_lib.erl 
Compiled src/sqlite3.erl 
==> erlang-sqlite (eunit) 
... 

回答

265

也许你在目录中有一个名为test一个文件/目录。如果此目录存在,并且没有更新的依赖关系,则该目标不会重建。

要强制重建这几样不是文件相关的目标,你应该让他们假如下:

.PHONY: all test clean 

请注意,你可以声明所有的伪目标在那里。

+0

我有一个名为build的目录,另一个名为lib。事后看来,这些并不是完美的目标名称。唉.....做。 – MattD 2013-10-15 20:35:28

+1

*其中'all','test'和'clear'是您的生成文件目标名称 – ThorSummoner 2015-04-27 17:05:17

+0

另一种解决方案是更改标签。在你的情况下,将'test'改为'test_rule'或者其他的东西。 – auraham 2015-11-12 16:42:49

8

编辑:这只适用于make的某些版本 - 你应该检查你的手册页。

您还可以将-B标志传递给make。根据手册页,这是:

-B, --always-make无条件地制定所有目标。

,如果你是在一个情况下,你不想编辑Makefile或更改你的测试文件夹的名称,以便将make -B test解决您的问题。

+0

'-B'是向后兼容模式对我来说...(FreeBSD,OS/GNU工具包似乎没有被指定有问题) – 2016-08-15 13:25:45

+0

哦,有趣的是......“--always-make”是否适合你? – jamesc 2016-08-15 13:28:39

+0

没有。 '.PHONY'目标似乎是一种可移植的,尽管...(至少对FreeBSD来说,并不确定Solaris这样的东西) – 2016-08-15 16:53:33

相关问题