How can I force gnu make to not build recipe in parallel?
This is a horrible kludge, but it will do the job:
b.cpp: a.cpp
c.cpp: b.cpp
Or if there are actually a lot of these, you can have a few stiff drinks and do this:
c-sources = $(sources:.xxx=.cpp)
ALLBUTFIRST = $(filter-out $(firstword $(c-sources)), $(c-sources))
ALLBUTLAST = $(filter-out $(lastword $(c-sources)), $(c-sources))
PAIRS = $(join $(ALLBUTLAST),$(addprefix :,$(ALLBUTFIRST)))
$(foreach pair,$(PAIRS),$(eval $(pair)))
(This works in GNUMake, I don't know about other versions.)
Solution 1
GNU Make contains the special built-in pseudo-target .NOTPARALLEL
Example:
.PHONY: all clean
.NOTPARALLEL:
anotherTarget: dependency1
Solution 2
You can also use the -j <n>
,--jobs[=<n>]
flag on the command line where n
is the number of recipies allowed to run in parallel.
Usage:
make -j <n>
or make --jobs=<n>
Example:
make -j 1
or make --jobs=1
note: omitting <n>
will allow an arbitrary number of recipes to be executed, only limited by your system's available resources
Solution 3
Finally, you can assign the command line flag in solution 2 to the MAKEFLAGS
variable from within your Makefile
Example:
MAKEFLAGS := -j 1
or
MAKEFLAGS := --jobs=1
A related solution is to specify the exact order you want things built (rather than saying, "don't build in parallel").
To specify the exact order, you can use order-only prerequisites. Here's GNU make's man page on it:
Occasionally, however, you have a situation where you want to impose a specific ordering on the rules to be invoked without forcing the target to be updated if one of those rules is executed. In that case, you want to define order-only prerequisites. Order-only prerequisites can be specified by placing a pipe symbol (|) in the prerequisites list: any prerequisites to the left of the pipe symbol are normal; any prerequisites to the right are order-only:
targets : normal-prerequisites | order-only-prerequisites
And here's the example they offer:
OBJDIR := objdir
OBJS := $(addprefix $(OBJDIR)/,foo.o bar.o baz.o)
$(OBJDIR)/%.o : %.c
$(COMPILE.c) $(OUTPUT_OPTION) $<
all: $(OBJS)
$(OBJS): | $(OBJDIR)
$(OBJDIR):
mkdir $(OBJDIR)
I had to use order only prerequisites on a make dist
rule due to a race condition. The dist
recipe depended on a distclean
and diff
rules, and the diff
rule performed an svn diff -r XXX
to show the exact changes. On occasion, make would delete the diff it just created because the clean rule would run after the diff rule.