353

This is my 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

I can run make compile multiple times and get

aromanov@alexey-desktop:~/workspace/gm-controller/lib/erlang-sqlite$ make compile
./rebar get-deps compile
==> erlang-sqlite (get-deps)
==> erlang-sqlite (compile)

However, for some reason running make test always gives

aromanov@alexey-desktop:~/workspace/gm-controller/lib/erlang-sqlite$ make test
make: `test' is up to date.

even if the files are not compiled. The question is, why?

Running the same command directly works:

aromanov@alexey-desktop:~/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)
...
Benjamin Loison
  • 3,782
  • 4
  • 16
  • 33
Alexey Romanov
  • 167,066
  • 35
  • 309
  • 487

4 Answers4

699

Maybe you have a file/directory named test in the directory. If this directory exists, and has no dependencies that are more recent, then this target is not rebuild.

To force rebuild on these kind of not-file-related targets, you should make them phony as follows:

.PHONY: all test clean

Note that you can declare all of your phony targets there.

A phony target is one that is not really the name of a file; rather it is just a name for a recipe to be executed when you make an explicit request.

Didier Trosset
  • 36,376
  • 13
  • 83
  • 122
  • 5
    I had a directory called build and another called lib. In hindsight, these are not perfect target names. Ugh.....make. – MattD Oct 15 '13 at 20:35
  • 21
    *Where `all`, `test`, and `clear` are your makefile target names – ThorSummoner Apr 27 '15 at 17:05
  • Another solution is changing the label. In your case, change `test` for `test_rule` or something different. – auraham Nov 12 '15 at 16:42
  • @MattD so do I, is that a problem for make? – birgersp Nov 15 '16 at 20:54
  • @Birger if you have targets that you want to invoke like "make build" and "make lib" and you have those directories present, then you will need to use this strategy or one like it. – MattD Nov 16 '16 at 16:31
  • In my case, I mistakenly place a folder with the same name (src) at the same directory with Makefile (e.g /src), so Makefile never reaches the real folder in /apps/src. – Lê Quang Duy Feb 05 '18 at 09:20
  • An explanation of what a "phony target" is would be super helpful for us noobs! This was the answer I needed, but I ignored it because I had no idea what a "phony target" was and I figured it was some advanced Make feature that wasn't related to what I wanted. – Mike B Sep 29 '20 at 20:40
  • @Soren There's no specific place where to add this in the Makefile. I usually place it right after the default generic rules, before the "actual files" rules. Just be careful not to add it in the middle of the commands of a rule. – Didier Trosset Sep 20 '21 at 10:10
79

It happens when you have a file with the same name as Makefile target name in the directory where the Makefile is present.

enter image description here

Piyush Sonigra
  • 1,423
  • 11
  • 10
60

EDIT: This only applies to some versions of make - you should check your man page.

You can also pass the -B flag to make. As per the man page, this does:

-B, --always-make Unconditionally make all targets.

So make -B test would solve your problem if you were in a situation where you don't want to edit the Makefile or change the name of your test folder.

jamesc
  • 5,852
  • 3
  • 32
  • 42
  • `-B` is backward-compatible mode for me... (FreeBSD, OS / GNU toolkit does not seem to be specified in question) – Gert van den Berg Aug 15 '16 at 13:25
  • Oh interesting... Does `--always-make` work for you? – jamesc Aug 15 '16 at 13:28
  • Nope. The `.PHONY` target seems kind of portable though... (At least to FreeBSD, not sure about things like Solaris) – Gert van den Berg Aug 15 '16 at 16:53
  • Thanks - I've edited the answer to include a warning. – jamesc Aug 16 '16 at 14:04
  • 2
    This defies the purpose of make - determining automatically which pieces of a program need to be rebuilt after a change. If your makefile needs the `--always-make` option to work, your makefile is broken. – osvein Jul 29 '17 at 09:28
  • 2
    @GertvandenBerg .PHONY is going to be part of issue 8 of the POSIX standard http://austingroupbugs.net/view.php?id=523 – osvein Jul 29 '17 at 09:31
6

my mistake was making the target name "filename.c:" instead of just "filename:"

ThorSummoner
  • 16,657
  • 15
  • 135
  • 147