Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

gmake compile all files in a directory

we have some C++ code that we need to create a make file in. Each .h and .C pair create an object and then some objects are linked together to form a executable. Pretty standard stuff.

This non-gnu make command just builds all the files into object in a directory

%.o:%.C
    $(CC) $(CPFLAGS)  -c  $<

What this does is for each %.C file (ie every .C file) build a corresponding .o file.

Does anybody know how to do this with gmake?

Cheers

Mark

like image 957
Mark Lakewood Avatar asked Aug 28 '09 03:08

Mark Lakewood


2 Answers

The syntax you've shown is called a pattern rule in GNU make parlance, and it forms the corner stone of your solution. All you need is to add a way to get the list of .C files dynamically. Others have shown solutions that use $(shell) to do this, but that's needlessly inefficient. I suggest you instead use $(wildcard), which is a GNU make built-in function designed for just this purpose:

SRCS = $(wildcard *.C)
OBJS = $(patsubst %.C,%.o,$(SRCS))
foo: $(OBJS)
        $(CC) -o $@ $^

%.o: %.C
        $(CC) $(CPFLAGS)  -c  $<

If you are looking for something more concise, the following will work too:

foo: $(patsubst %.C,%.o,$(wildcard *.C))

This just eliminates the variables and takes advantage of the fact that GNU make provides a default %.o: %.C pattern rule, as well as a default rule for linking an executable together from a set of objects. Personally I would use the more verbose version as I find it easier to read and maintain, but to each their own.

Hope that helps,

Eric Melski

like image 51
Eric Melski Avatar answered Oct 13 '22 20:10

Eric Melski


This is an example of a pattern rule, it should work fine in gmake. For very simple builds like this you can mostly rely on the implicit rules. The main thing you have to specify in the target you want to build and its dependencies:

CXXFLAGS:=-g -O -Iincludes
LDFLAGS:=-lm

SRCS:=$(shell ls *.C)          # select all .C files as source
OBJS:=$(substr .C,.o,$(SRCS)   # list the corresponding object files

foo : $(OBJS)

Note the use of simply expanded variable assignment operator (:=) rather than the recursive assignment operator (=) which can reduce the amount of reprocessing make does in more complicated builds.

like image 21
dmckee --- ex-moderator kitten Avatar answered Oct 13 '22 19:10

dmckee --- ex-moderator kitten