开发者

Persistent Makefile Variables

I want my Makefile to be invoked like this:

make x11 oss bin

which should result in compiling the files: main.c x11.c oss.c and link them into one executable file bin.

Another way to invoke it would be:

make x11 alsa bin

which should do the same thing 开发者_JS百科but with main.c x11.c alsa.c

This is my Makefile:

bin: $(OBJ) main.o
    $(CC) $(LDFLAGS) $(OBJ) main.o $(LDLIBS)
x11:
    set OBJ += bsd.o
oss:
    set OBJ += oss.o
alsa:
    set OBJ += alsa.o
.c.o:
    $(CC) $(CFLAGS) -c $<

but it seems that the contents of the OBJ variable isn't persistent throughout the recipes. Any suggestions?


OBJ is persistent, but you have another problem:

  • The Makefile first is completely parsed by make. And thus $OBJ still is unset/empty in this stage. Therefore, the bin target only gets main.o as dependency since all variables are replaced with their value in this stage.
  • Next, OBJ is being updated with its content using the given targets on the command line. But OBJ is not used anymore for the bin target, since make is finihed building the dependencies already. (Makefile normally is not parsed a second time)

The trick is to have the OBJ variable filled before the parsing. A simple solution is to call the Makefile using:

make "OBJ=x11 oss" bin

and modify the Makefile a bit to have the .o-part added (or just add them to the make command):

bin: $(patsubst %,%.o,$(OBJ)) main.o
    $(CC) $(LDFLAGS) $(OBJ) main.o $(LDLIBS)
.c.o:
    $(CC) $(CFLAGS) -c $<

Note: I said 'Makefile normally is not parsed a second time'. It is possible to recursively use the Makefile multiple times. This is very complicated and probably not required for 99% of all cases. An example of such 'make abuse' is the OpenWRT buildsystem. trunk/Makefile is an example of a Makefile is is called multiple times by itself.


This is somewhat of a hack.

Add this like to the top of your Makefile:

OBJ := $(filter-out bin,${MAKECMDGOALS})

Now when you type make x11 oss bin make parses this:

OBJ := x11 oss

and for make x11 alsa bin it will see

OBJ := x11 alsa

You will probably have to remove the shell commands for x11 et. al. as set OBJ += bsd.o is not valid shell.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜