summaryrefslogtreecommitdiff
path: root/build
diff options
context:
space:
mode:
authorNicolas Schodet2015-05-15 12:05:06 +0200
committerNicolas Schodet2019-10-07 00:44:50 +0200
commit41fde87ed8d1fcd593777bdfae2fa9e65006d984 (patch)
tree48a82b5ba790741d1f0bcc97eb183ea4b045d7b0 /build
parent751a7d2ba7a0fbb9c6dae2d91891f0cc74897a2a (diff)
build: add support for out of tree modules
Diffstat (limited to 'build')
-rw-r--r--build/arch.mk18
-rw-r--r--build/config.mk5
-rw-r--r--build/macros.mk20
-rw-r--r--build/setup.mk11
-rw-r--r--build/stm32.mk4
-rw-r--r--build/stm32f1.mk2
-rw-r--r--build/stm32f4.mk2
-rwxr-xr-xbuild/tools/config-gen6
-rw-r--r--build/top.mk27
9 files changed, 65 insertions, 30 deletions
diff --git a/build/arch.mk b/build/arch.mk
index 99f0c5f..1668bb8 100644
--- a/build/arch.mk
+++ b/build/arch.mk
@@ -40,21 +40,24 @@ elf.$1: $$($1_ELFS)
define $1_PROG_template
$$1.$1$$$$($1_ELF_SUFFIX): $$$$(patsubst %,$$(OBJDIR)/%.$1.o,\
$$$$(call filter_sources,$1,$$$$($$1_SOURCES)))
- @echo "LINK [$1] $$$$@: $$$$(notdir $$$$^)"
+ @echo "LINK [$1] $$$$@"
$$$$Q$$$$($1_LINK.$$(call iscxx,$$($$1_SOURCES))) $$$$^ $$$$($1_LDLIBS) -o $$$$@
endef
$$(foreach prog,$$($1_PROGS),$$(eval $$(call $1_PROG_template,$$(prog))))
-$$(OBJDIR)/%.$1.o: %.c $$(COMPILE_DEPS) | $$(OBJDIR) $$(COMPILE_ORDER_DEPS)
+$$(OBJDIR)/%.$1.o: %.c $$(COMPILE_DEPS) | $$(COMPILE_ORDER_DEPS)
@echo "CC [$1] $$<"
+ $$(call mkdir_if_needed,$$@)
$$Q$$($1_COMPILE.c) -o $$@ $$<
-$$(OBJDIR)/%.$1.o: %.cc $$(COMPILE_DEPS) | $$(OBJDIR) $$(COMPILE_ORDER_DEPS)
+$$(OBJDIR)/%.$1.o: %.cc $$(COMPILE_DEPS) | $$(COMPILE_ORDER_DEPS)
@echo "CXX [$1] $$<"
+ $$(call mkdir_if_needed,$$@)
$$Q$$($1_COMPILE.cc) -o $$@ $$<
-$$(OBJDIR)/%.$1.o: %.S $$(COMPILE_DEPS) | $$(OBJDIR) $$(COMPILE_ORDER_DEPS)
+$$(OBJDIR)/%.$1.o: %.S $$(COMPILE_DEPS) | $$(COMPILE_ORDER_DEPS)
@echo "AS [$1] $$<"
+ $$(call mkdir_if_needed,$$@)
$$Q$$($1_COMPILE.S) -o $$@ $$<
# Dependency checking.
@@ -115,7 +118,7 @@ bin.$1: $$($1_PROGS:%=%.$1.bin)
$$Q$$($1_OBJCOPY) -O binary $$< $$@
crc.$1: $$($1_PROGS:%=%.$1.bin)
- $Q$$(BASE)/build/tools/crc $$^
+ $$Q$$(UCOO_BASE)/build/tools/crc $$^
$1_EXTRA_CLEAN += $$($1_PROGS:%=%.$1.hex) \
$$($1_PROGS:%=%.$1.srec) \
@@ -146,6 +149,9 @@ define arch_misc_rules
clean: clean.$1
clean.$1:
- rm -f $$(OBJDIR)/*.$1.[od] $$($1_ELFS) $$($1_EXTRA_CLEAN)
+ @echo rm -f '$$(OBJDIR)/.../*.$1.[od]' $$($1_ELFS) $$($1_EXTRA_CLEAN)
+ $$Qrm -f $$(patsubst %,$$(OBJDIR)/%.$1.[od],\
+ $$(call filter_sources,$1,$$(ALL_SOURCES))) \
+ $$($1_ELFS) $$($1_EXTRA_CLEAN)
endef
diff --git a/build/config.mk b/build/config.mk
index e5be30f..460eeaa 100644
--- a/build/config.mk
+++ b/build/config.mk
@@ -3,7 +3,8 @@
# Build time configuration system.
PROJECT_CONFIG ?= Config
-MODULES_CONFIG := $(wildcard $(ALL_MODULES:%=$(BASE)/ucoo/%/Config))
+MODULES_CONFIG := $(wildcard $(ALL_UCOO_MODULES:%=$(UCOO_BASE)/%/Config)) \
+ $(wildcard $(ALL_EXT_MODULES:%=$(BASE)/%/Config))
CONFIG_LIST := $(strip $(wildcard $(PROJECT_CONFIG)) $(MODULES_CONFIG))
@@ -27,7 +28,7 @@ clean: config-clean
$(OBJDIR)/config.list: $(CONFIG_LIST) $(CONFIG_FORCE) | $(OBJDIR)
@echo "CONF $(PROJECT_CONFIG)"
- $Q$(BASE)/build/tools/config-gen -H $(OBJDIR)/config/%.hh \
+ $Q$(UCOO_BASE)/build/tools/config-gen -H $(OBJDIR)/config/%.hh \
-p $(PROJECT_CONFIG) -T '$(TARGETS_SUBTARGETS)' \
$(MODULES_CONFIG)
$Qecho "CONFIG_LIST_OLD = $(CONFIG_LIST)" > $@
diff --git a/build/macros.mk b/build/macros.mk
index 8ae3244..f06e9b3 100644
--- a/build/macros.mk
+++ b/build/macros.mk
@@ -15,3 +15,23 @@ filter_sources_sub = $(foreach t,$1 $($1_SUBTARGETS),$(filter %.$t,$2)) \
# Test if one of the source is C++, in this case, return cc, else return c.
# $(call iscxx,SOURCES)
iscxx = $(if $(filter %.cc,$1),cc,c)
+
+# Output every parent directories until root is reached.
+# $(call parents,DIRS,ROOT)
+parents = $(foreach d,$1,$(call parents_sub,$d,$2))
+parents_sub = $(if $(filter-out $2,$1),\
+ $(filter-out %/,$1) \
+ $(call parents_sub,$(patsubst %/,%,$(dir $1)),$2))
+
+# Reverse a list.
+# $(call reverse,A B C...)
+reverse = $(if $1,$(call reverse,$(wordlist 2,$(words $1),$1))) $(firstword $1)
+
+# Run mkdir if directory does not exists.
+# $(call mkdir_if_needed,FILE)
+mkdir_if_needed = $(if $(wildcard $(dir $1)),,$Qmkdir -p $(dir $1))
+
+# Try to rmdir empty directories.
+# $(call rmdir_as_needed,DIRS,ROOT)
+rmdir_as_needed = $Qrmdir $(call reverse,$(sort $(call parents,$1,$2))) \
+ $2 2>/dev/null || true
diff --git a/build/setup.mk b/build/setup.mk
index a48a4f9..178f070 100644
--- a/build/setup.mk
+++ b/build/setup.mk
@@ -4,23 +4,28 @@
TARGETS ?= host
-DEFAULT_MODULES ?= intf arch arch/host arch/host/mex
+DEFAULT_MODULES ?= ucoo/intf ucoo/arch ucoo/arch/host ucoo/arch/host/mex
ALL_PROGS := $(PROGS) $(foreach target,$(TARGETS),$($(target)_PROGS))
ALL_MODULES := $(sort $(DEFAULT_MODULES) $(MODULES) \
$(foreach prog,$(ALL_PROGS),$($(prog)_MODULES)))
+ALL_UCOO_MODULES := $(filter ucoo/%,$(ALL_MODULES))
+ALL_EXT_MODULES := $(filter-out ucoo/%,$(ALL_MODULES))
-include $(ALL_MODULES:%=$(BASE)/ucoo/%/Module)
+include $(ALL_UCOO_MODULES:%=$(UCOO_BASE)/%/Module)
+include $(ALL_EXT_MODULES:%=$(BASE)/%/Module)
define MODULES_template
$1_SOURCES += $$(foreach module,\
$$(DEFAULT_MODULES) $$(call defval,$1_MODULES,$$(MODULES)),\
- $$($$(subst /,_,$$(module))_SOURCES)\
+ $$(addprefix $$(module)/,$$($$(subst /,_,$$(module))_SOURCES))\
)
endef
$(foreach prog,$(ALL_PROGS),$(eval $(call MODULES_template,$(prog))))
ALL_SOURCES := $(foreach prog,$(ALL_PROGS),$($(prog)_SOURCES))
+OBJDIRS := $(sort $(dir $(ALL_SOURCES:%=$(OBJDIR)/%)))
+
COMPILE_DEPS :=
diff --git a/build/stm32.mk b/build/stm32.mk
index b811f0c..0bc43a1 100644
--- a/build/stm32.mk
+++ b/build/stm32.mk
@@ -7,7 +7,7 @@ stm32_once := 1
# Check for libopencm3.
-LIBOPENCM3_PATH ?= $(BASE)/lib/libopencm3
+LIBOPENCM3_PATH ?= $(UCOO_BASE)/lib/libopencm3
define stm32_libopencm3
ifneq ($$(LIBOPENCM3_PATH),)
$1_LIBOPENCM3_LIB := $$(LIBOPENCM3_PATH)/lib/libopencm3_$1.a
@@ -37,7 +37,7 @@ $1_CXXFLAGS := $$(sort $$($1_CFLAGS) $$(CXXFLAGS))
$1_ASFLAGS := $$(ASFLAGS)
$1_LDSCRIPT := $1.ld
$1_LDFLAGS := $$(LDFLAGS) -T$$($1_LDSCRIPT) \
- -L$$(BASE)/ucoo/arch/$1 \
+ -L$$(UCOO_BASE)/ucoo/arch/$1 \
$$($1_LIBOPENCM3_LDFLAGS)
$1_LDLIBS := -nostartfiles $$(LDLIBS) $$($1_LIBS) \
-lopencm3_$1
diff --git a/build/stm32f1.mk b/build/stm32f1.mk
index 6e65bef..6cd79f2 100644
--- a/build/stm32f1.mk
+++ b/build/stm32f1.mk
@@ -2,7 +2,7 @@
#
# Rules for STM32F1.
-include $(BASE)/build/stm32.mk
+include $(UCOO_BASE)/build/stm32.mk
$(eval $(call stm32_libopencm3,stm32f1))
diff --git a/build/stm32f4.mk b/build/stm32f4.mk
index 648bcab..106ef22 100644
--- a/build/stm32f4.mk
+++ b/build/stm32f4.mk
@@ -2,7 +2,7 @@
#
# Rules for STM32F4.
-include $(BASE)/build/stm32.mk
+include $(UCOO_BASE)/build/stm32.mk
$(eval $(call stm32_libopencm3,stm32f4))
diff --git a/build/tools/config-gen b/build/tools/config-gen
index 9bc578b..be3dac2 100755
--- a/build/tools/config-gen
+++ b/build/tools/config-gen
@@ -105,14 +105,14 @@ def write_header(filename, section, section_dict):
for target, value in values.iteritems():
if target is None: continue
item_fmt = ('#ifdef TARGET_{target}\n'
- '# define UCOO_CONFIG_{section}_{key} ({value})\n'
+ '# define CONFIG_{section}_{key} ({value})\n'
'#endif')
items.append(item_fmt.format(section=section, key=key.upper(),
target=target, value=value))
cond = True
- item_fmt = '#define UCOO_CONFIG_{section}_{key} ({value})'
+ item_fmt = '#define CONFIG_{section}_{key} ({value})'
if cond:
- item_fmt = '#ifndef UCOO_CONFIG_{section}_{key}\n# ' \
+ item_fmt = '#ifndef CONFIG_{section}_{key}\n# ' \
+ item_fmt[1:] + '\n#endif'
items.append(item_fmt.format(section=section, key=key.upper(),
value=values[None]))
diff --git a/build/top.mk b/build/top.mk
index 385df77..f3c6ccc 100644
--- a/build/top.mk
+++ b/build/top.mk
@@ -1,19 +1,21 @@
# ucoolib - Microcontroller object oriented library.
#
-# Build system top file. To be included with $(BASE) pointing to the ucoolib
+# Build system top file. To be included with $(BASE) pointing to the project
# root.
ifeq ($(BASE),)
$(error BASE is not defined)
endif
-include $(BASE)/build/macros.mk
+UCOO_BASE := $(patsubst %/build/top.mk,%,$(lastword $(MAKEFILE_LIST)))
+
+include $(UCOO_BASE)/build/macros.mk
# General parameters.
OBJDIR := obj
-INCLUDES := $(INCLUDES) -I$(BASE) -I$(OBJDIR)
+INCLUDES := $(INCLUDES) -I$(UCOO_BASE) -I$(BASE) -I$(OBJDIR)
CPPFLAGS := $(DEFS) $(INCLUDES) -MP -MMD
OPTIMIZE ?= -Os
CFLAGS := -g -Wall -W -Wundef -Wno-unused-parameter \
@@ -36,32 +38,33 @@ bin:
crc:
clean:
- rmdir $(OBJDIR) 2> /dev/null || true
+ @echo rmdir '$(OBJDIR)/.../'
+ $(call rmdir_as_needed,$(OBJDIRS),$(OBJDIR))
.PHONY: all lst size hex srec bin crc clean
# Modules and sources setup.
-include $(BASE)/build/setup.mk
+include $(UCOO_BASE)/build/setup.mk
-vpath %.cc $(ALL_MODULES:%=$(BASE)/ucoo/%)
-vpath %.c $(ALL_MODULES:%=$(BASE)/ucoo/%)
-vpath %.S $(ALL_MODULES:%=$(BASE)/ucoo/%)
+vpath %.cc $(UCOO_BASE) $(BASE)
+vpath %.c $(UCOO_BASE) $(BASE)
+vpath %.S $(UCOO_BASE) $(BASE)
# Configuration.
-include $(BASE)/build/config.mk
+include $(UCOO_BASE)/build/config.mk
# Objects directory.
$(OBJDIR):
- $Qmkdir -p $(OBJDIR)
+ $Qmkdir -p $@
# Arch specific.
-include $(BASE)/build/arch.mk
+include $(UCOO_BASE)/build/arch.mk
define TARGETS_template
-include $$(BASE)/build/$1.mk
+include $$(UCOO_BASE)/build/$1.mk
endef
$(foreach target,$(TARGETS),$(eval $(call TARGETS_template,$(target))))