Inspired by the article "Recursive Make Considered Harmful" by Peter Miller (http://aegis.sourceforge.net/auug97.pdf)
And with the aid
of this link http://www.xs4all.nl/~evbergen/nonrecursive-make.html which propose a way to implement
it.
I sat down learned all
I needed to know about makefiles and started creating my own non recursive
makefile scheme...
I will describe the bug
first (as this is the propose of this mailing list) but I would love to get
feedback on my makefile scheme... which will described immediately
after.
The
bug:
In my make files
fragments which are called sub.make in my script I have "%.a" targets. each
makefile fragment includes a Rules.make in the top dir. This centralized
Rule.make has a general rule for %.a targets.
For some reason the
dependencies of these targets gets wipeout!
My
scheme:
1. I do not iterate
over all the subdirs. just the one that are set in each make
fragments
2. In my tree the
source is set apart from the makefiles. Imagine that you have two identical
directory trees one containing only makefiles and make fragments. the other only
source file.
3. for this example I
describe a next tree dir:
/dir1
/dir2
/dir2/dir2a
/dir2/dir2b
/dir3/dir3a
TOP level
makefile:
# The root directory of
the sub.make files
TOPDIR := /path/to/makefile/dir
TOPDIR := /path/to/makefile/dir
# The root directory of
the src (may be eq to TOPDIR)
TOPSRC := /path/to/identical/src/tree
TOPSRC := /path/to/identical/src/tree
# Only in top
make
CURRDIR := $(TOPDIR)
SRCDIR := $(TOPSRC)
D = $(SRCDIR)
CURRDIR := $(TOPDIR)
SRCDIR := $(TOPSRC)
D = $(SRCDIR)
# Linux
Defines
TOPDEF := __KERNEL__ MODULE MODVERSIONS EXPORT_SYMTAB
TOPDEF := __KERNEL__ MODULE MODVERSIONS EXPORT_SYMTAB
#subdirs
SUBDIRS := dir1 dir2 dir3/dir3a
SUBDIRS := dir1 dir2 dir3/dir3a
.PHONY:
all
all: $(SRCDIR)/all
system.o
system.o: sys_part1.a sys_part2.a
$(LD) -r -o $@ -Map $*.map $^
$(LD) -r -o $@ -Map $*.map $^
include
$(TOPDIR)/Rules.make
The
Rule.make:
# Save Target Specific
Variables
$(OBJ): T_DIR := $(SRCDIR)
$(OBJ): T_INC := $(addprefix $(SRCDIR)/,$(INC)) $(addprefix $(TOPSRC)/,$(TOPINC))
$(OBJ): T_DEF := $(DEF)
$(LIB): T_OBJ := $(OBJ)
$(patsubst %.o, %.d,$(OBJ)): T_INC := $(addprefix $(SRCDIR)/,$(INC)) $(addprefix $(TOPSRC)/,$(TOPINC))
$(patsubst %.o, %.d,$(OBJ)): T_DEF := $(DEF)
$(OBJ): T_DIR := $(SRCDIR)
$(OBJ): T_INC := $(addprefix $(SRCDIR)/,$(INC)) $(addprefix $(TOPSRC)/,$(TOPINC))
$(OBJ): T_DEF := $(DEF)
$(LIB): T_OBJ := $(OBJ)
$(patsubst %.o, %.d,$(OBJ)): T_INC := $(addprefix $(SRCDIR)/,$(INC)) $(addprefix $(TOPSRC)/,$(TOPINC))
$(patsubst %.o, %.d,$(OBJ)): T_DEF := $(DEF)
# Common rules
%.o: $(SRCDIR)/%.c %.d
$(CC) $(addprefix -I, $(T_INC)) $(addprefix -D, $(T_DEF)) -o $@ -c $<
%.o: $(SRCDIR)/%.c %.d
$(CC) $(addprefix -I, $(T_INC)) $(addprefix -D, $(T_DEF)) -o $@ -c $<
THIS
IS THE BUG
#FIXME: this rule does
not take affect for some reason
%.a: $(OBJ)
$(LD) -r -o $@ $(T_OBJ)
%.a: $(OBJ)
$(LD) -r -o $@ $(T_OBJ)
%.d:
$(SRCDIR)/%.c
$(CC) -MD -E $(addprefix -I, $(T_INC)) $(addprefix -D, $(T_DEF)) -o $@ -c $<
$(CC) -MD -E $(addprefix -I, $(T_INC)) $(addprefix -D, $(T_DEF)) -o $@ -c $<
DEP := $(patsubst %.o,
%.d,$(OBJ))
ifeq ($(words $(DEP)), 0)
#do nothing
else
include $(DEP)
endif
ifeq ($(words $(DEP)), 0)
#do nothing
else
include $(DEP)
endif
##############################
# Sub directories itteration #
##############################
# Sub directories itteration #
##############################
#Add the sub dir target
to this dir target dependency list and declare them phony
SUBDIRTARGET := $(addsuffix /all, $(addprefix $(strip $(SRCDIR))/, $(SUBDIRS)))
.PHONY: $(SUBDIRTARGET)
$(SRCDIR)/all: $(SUBDIRTARGET)
SUBDIRTARGET := $(addsuffix /all, $(addprefix $(strip $(SRCDIR))/, $(SUBDIRS)))
.PHONY: $(SUBDIRTARGET)
$(SRCDIR)/all: $(SUBDIRTARGET)
#Add the new this
target new sub dirs to the SUBDIRS_QUEUE queue
NEWSUBS := $(addprefix $(strip $(SRCDIR))/, $(SUBDIRS))
SUBDIRS_QUEUE += $(NEWSUBS)
NEWSUBS := $(addprefix $(strip $(SRCDIR))/, $(SUBDIRS))
SUBDIRS_QUEUE += $(NEWSUBS)
#Pop the next sub dir
to be proccessed
SRCDIR := $(word 1, $(SUBDIRS_QUEUE))
SUBDIRS_QUEUE := $(wordlist 2,$(words $(SUBDIRS_QUEUE)),$(SUBDIRS_QUEUE))
SRCDIR := $(word 1, $(SUBDIRS_QUEUE))
SUBDIRS_QUEUE := $(wordlist 2,$(words $(SUBDIRS_QUEUE)),$(SUBDIRS_QUEUE))
SUBDIRS :=
ifeq ($(words $(SRCDIR)), 0)
#do nothing
else
include $(patsubst $(TOPSRC)%, $(TOPDIR)%, $(SRCDIR)/sub.make)
endif
ifeq ($(words $(SRCDIR)), 0)
#do nothing
else
include $(patsubst $(TOPSRC)%, $(TOPDIR)%, $(SRCDIR)/sub.make)
endif
Exmaple of a
dir sub make "dir2/sub.make" :
LIB :=
sys_part1.a
OBJ := first_file.o
second_file.o ...
INC :=
.
TOPINC:= inc
DEF := $(TOPDEF)
SUBDIRS := dir2a dir2b
TOPINC:= inc
DEF := $(TOPDEF)
SUBDIRS := dir2a dir2b
$(D)/all: $(OBJ)
$(LIB)
include $(TOPDIR)/Rules.make
include $(TOPDIR)/Rules.make
--------------------------------------------------------------------------------------
One last question:
looking for a place to post this story (sorry for the length) I have seen the
last real thread was somewhere in 2002.
where most of them date back to
1999 and earlier.
In the mean time has someone
seen the light and produced "the best ever makefile
scheme"
10x
Eran
Liberty
_______________________________________________ Bug-make mailing list [EMAIL PROTECTED] http://lists.gnu.org/mailman/listinfo/bug-make