-
Notifications
You must be signed in to change notification settings - Fork 5
Expand file tree
/
Copy pathMakefile
More file actions
169 lines (139 loc) · 4.92 KB
/
Makefile
File metadata and controls
169 lines (139 loc) · 4.92 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
CROSS ?= arm-none-eabi-
ifneq ($(OS),Windows_NT)
CCACHE ?= $(shell which ccache)
ifeq ($(shell which $(CROSS)gcc),)
CROSS := arm-elf-eabi-
endif
endif
FLTO ?= -flto -flto-partition=none
ifeq ($(shell $(CROSS)gcc -v --help 2>/dev/null | grep -- -flto),)
FLTO :=
endif
CC := $(CCACHE) $(CROSS)gcc
LD := $(CROSS)ld
OBJCOPY := $(CROSS)objcopy
OBJDUMP := $(CROSS)objdump
CFLAGS_GENERAL := -c -ffunction-sections -fdata-sections -fmessage-length=0 -Wall -Wno-packed-bitfield-compat $(CFLAGS_GENERAL)
CFLAGS_ASM := -x assembler-with-cpp $(CFLAGS_ASM)
CFLAGS_CXX := -fno-exceptions -fno-rtti -std=gnu++11 $(CFLAGS_CXX)
CFLAGS_debug := -O0 -g3 -gdwarf-2 $(CFLAGS_DEBUG)
CFLAGS_release := $(FLTO) -Os -fno-pie -fno-stack-protector -fomit-frame-pointer -g3 -gdwarf-2 $(CFLAGS_RELEASE)
LDFLAGS_GENERAL := -nostdlib --gc-sections $(LDFLAGS_GENERAL)
LDFLAGS_debug := -O0 $(LDFLAGS_DEBUG)
LDFLAGS_release := $(FLTO) -Os $(LDFLAGS_RELEASE)
PPFLAGS_GENERAL := -DTARGET_$(subst /,_,$(TARGET)) -DTARGET=$(TARGET) -DCONFIG_H=target/$(TARGET)/config.h -DTARGET_H=target/$(TARGET)/target.h -Isrc
PPFLAGS_debug := -DDEBUG
PPFLAGS_release := -DRELEASE
PPONLY_FLAGS := -E -P -x c -DASM_FILE
SPEC_FLAGS := -E -P -v -dD
ifeq ($(VERY_VERBOSE),)
VQ := @
else
VERBOSE := 1
endif
ifeq ($(VERBOSE),)
Q := @
endif
CWD := $(shell pwd)
relpath = $(patsubst $(CWD)/%,%,$(realpath $(1)))
preprocess = $(shell $(CC) $(2) $(PPONLY_FLAGS) $(1) | grep -v "^\#")
preprocesspaths = $(shell $(CC) $(2) $(PPONLY_FLAGS) $(1) | grep -v "^\#" | sed -e "s:^ *::;s:^..*:$(dir $(1))&:;s:^\\./::")
TARGETS := $(call preprocess,TARGETS,-I.)
ACTIVE := $(call preprocess,src/target/ACTIVE,-I.)
ifeq ($(TARGET),)
all: $(TARGETS)
active:
$(VQ)-mkdir -p build/ACTIVE
$(Q)+$(MAKE) $(ACTIVE) COPYTO=build/ACTIVE/firmware COPYCTL=src/target/ACTIVE
define TARGET_template
$(1):
$(Q)+$(MAKE) TARGET=$(1)
endef
$(foreach target,$(TARGETS),$(eval $(call TARGET_template,$(target))))
else
ifneq ($(TYPE),debug)
ifneq ($(TYPE),release)
$(error Please define either TYPE=debug or TYPE=release)
endif
endif
ifeq ($(LISTING),)
all: $(TARGET)
else
all: $(TARGET) LISTINGS
endif
_PPFLAGS := $(PPFLAGS_GENERAL) $(PPFLAGS_$(TYPE)) $(PPFLAGS)
define MODULE_template
ifeq ($(1),)
$$(shell echo Cannot resolve module $(2) 1>&2)
else
ifeq ($$(filter $(1),$$(INCLUDED_MODULES)),)
INCLUDED_MODULES += $(1)
ifneq ($(VERBOSE),)
$$(shell echo Including module $(1) 1>&2)
endif
-include $(1)/target.mk
ifneq ($(wildcard $(1)/SOURCES),)
SOURCES += $(1)/SOURCES
SRC += $$(call preprocesspaths,$(1)/SOURCES,$$(_PPFLAGS))
endif
ifneq ($(wildcard $(1)/DEPS),)
DEPS += $(1)/DEPS
$$(foreach module,$$(strip $$(call preprocesspaths,$(1)/DEPS,$$(_PPFLAGS))),$$(eval $$(call MODULE_template,$$(call relpath,$$(module)),$$(module))))
endif
else
ifneq ($(VERY_VERBOSE),)
$$(shell echo Module $(1) is already included 1>&2)
endif
endif
endif
endef
$(eval $(call MODULE_template,src,src))
SRC := $(foreach file,$(SRC),$(call relpath,$(file)))
OBJ := $(SRC:src/%.c=build/$(TARGET)/$(TYPE)/%.o)
OBJ := $(OBJ:src/%.cpp=build/$(TARGET)/$(TYPE)/%.o)
OBJ := $(OBJ:src/%.S=build/$(TARGET)/$(TYPE)/%.o)
_LDSCRIPT := $(LDSCRIPT:src/%.lds=build/$(TARGET)/$(TYPE)/%.lds)
_ASMFLAGS := $(CFLAGS_GENERAL) $(CFLAGS_ASM) $(CFLAGS_$(TYPE)) $(_CFLAGS) $(_PPFLAGS) $(CFLAGS) $(ASMFLAGS)
_CXXFLAGS := $(CFLAGS_GENERAL) $(CFLAGS_CXX) $(CFLAGS_$(TYPE)) $(_CFLAGS) $(_PPFLAGS) $(CFLAGS) $(CXXFLAGS)
_CFLAGS := $(CFLAGS_GENERAL) $(CFLAGS_$(TYPE)) $(_CFLAGS) $(_PPFLAGS) $(CFLAGS)
_LDFLAGS := $(LDFLAGS_GENERAL) $(LDFLAGS_$(TYPE)) $(_LDFLAGS) $(LDFLAGS)
define CCRULE_template
build/$(TARGET)/$(TYPE)/%.$(1): src/%.$(2)
$(VQ)echo $(4) $$<
$(VQ)-mkdir -p $$(dir $$@)
$(VQ)rm -f $$@
$(VQ)$(3) -MM $(5) $$< > $$@.dep.tmp
$(VQ)sed -e "s|.*:|$$@:|" < $$@.dep.tmp > $$@.dep
$(VQ)sed -e 's/.*://' -e 's/\\$$$$//' < $$@.dep.tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$$$/:/' >> $$@.dep
$(VQ)rm -f $$@.dep.tmp
$(Q)$(3) -Wa,-adhlns="build/$(TARGET)/$(TYPE)/$$*.lst" $(5) -o $$@ $$<
endef
-include $(OBJ:%=%.dep)
build/$(TARGET)/$(TYPE)/%.bin: build/$(TARGET)/$(TYPE)/%.elf $(COPYCTL)
$(VQ)echo "[OC] " $<
$(Q)$(OBJCOPY) -O binary $< $@
ifneq ($(COPYTO),)
$(VQ)cp $@ $(COPYTO).bin
endif
build/$(TARGET)/$(TYPE)/$(NAME).elf: $(_LDSCRIPT) $(OBJ) $(SOURCES) $(DEPS) $(COPYCTL)
$(VQ)echo "[LD] " $@
$(Q)$(LD) -Map "$@.map" $(_LDFLAGS) -o $@ -T $(_LDSCRIPT) $(OBJ)
ifneq ($(COPYTO),)
$(VQ)cp $@ $(COPYTO).elf
$(VQ)cp $@.map $(COPYTO).elf.map
endif
%.lst: %
$(VQ)echo "[OD] " $<
$(Q)$(OBJDUMP) -S $< > $@
LISTINGS: $(OBJ:%=%.lst)
$(eval $(call CCRULE_template,lds,lds,$(CC),"[PP] ",$(_PPFLAGS) $(PPONLY_FLAGS)))
$(eval $(call CCRULE_template,o,cpp,$(CC),"[CC] ",$(_CXXFLAGS)))
$(eval $(call CCRULE_template,o,c,$(CC),"[CC] ",$(_CFLAGS)))
$(eval $(call CCRULE_template,o,S,$(CC),"[CC] ",$(_CFLAGS)))
endif
spec:
$(Q)$(CC) $(_CXXFLAGS) $(SPEC_FLAGS) src/spec.cpp
clean:
$(Q)rm -rf build
.SUFFIXES:
.PHONY: all active spec clean $(TARGETS) SOURCES DEPS LISTINGS