Makefile.top 8.58 KB
Newer Older
1 2 3 4 5 6 7
all:

# To be filled in by included makefiles
TARGETS =
BINARIES =
DOCS =

Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
8 9 10 11
ifndef LANG_MODE
	LANG_MODE := c
endif
ifeq ($(LANG_MODE),c)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
12
	COMPILER := CC
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
13
	FLAGS := C
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
14
	STANDARD := gnu99
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
15 16
endif
ifeq ($(LANG_MODE),cpp)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
17
	COMPILER := CXX
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
18
	FLAGS := CXX
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
19
	STANDARD := gnu++11
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
20
endif
21 22
# Build compiler flags
ifdef RELEASE
23
	CFLAGS += -O2 -ggdb2
24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39
else
	CFLAGS += -ggdb3 -O0 -DDEBUG
endif
ifeq ($(TARGET),mips)
	CC = mips-softfloat-linux-uclibc-gcc
endif
ifdef VERBOSE
	Q=
	M=@\#
else
	Q=@
	M=@echo " "
endif
ifndef PLUGIN_PATH
	PLUGIN_PATH := lib
endif
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
40 41
CFLAGS_ALL += $(CFLAGS) --std=$(STANDARD) -pedantic -Wall -Wextra -fno-omit-frame-pointer -DOUTPUT_DIRECTORY=\"$(abspath $(O))\" -DSOURCE_DIRECTORY=\"$(abspath $(S))\" -DPAGE_SIZE=$(PAGE_SIZE) -DPREFIX=$(abspath $(O)) -DMAX_LOG_LEVEL=$(MAX_LOG_LEVEL) -DPLUGIN_PATH=\"$(PLUGIN_PATH)\" $(addprefix -D,$(EXTRA_DEFINES))
CXXFLAGS_ALL += $(CXXFLAGS) $(CFLAGS) --std=$(STANDARD) -pedantic -Wall -Wextra -fno-omit-frame-pointer -DOUTPUT_DIRECTORY=\"$(abspath $(O))\" -DSOURCE_DIRECTORY=\"$(abspath $(S))\" -DPAGE_SIZE=$(PAGE_SIZE) -DPREFIX=$(abspath $(O)) -DMAX_LOG_LEVEL=$(MAX_LOG_LEVEL) -DPLUGIN_PATH=\"$(PLUGIN_PATH)\" $(addprefix -D,$(EXTRA_DEFINES))
42
LDFLAGS_ALL += $(LDFLAGS)
43 44 45 46 47
ifdef COV
CFLAGS_ALL += -fprofile-arcs -ftest-coverage -DCOVERAGE
CXXFLAGS_ALL += -fprofile-arcs -ftest-coverage -DCOVERAGE
LDFLAGS_ALL += -fprofile-arcs
endif
48 49

ifdef STATIC
50
	STATIC_LOCAL := 1
51
	STATIC_SYSTEM := 1
52 53
endif
ifdef STATIC_LOCAL
54
	CFLAGS_ALL += -static -DSTATIC
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
55
	CXXFLAGS_ALL += -static -DSTATIC
56 57
endif
ifdef STATIC_SYSTEM
58 59
	LDFLAGS_ALL += -static
endif
60
CFLAGS += $(addprefix -I,$(EXTRA_INCLUDES))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
61
CXXFLAGS += $(addprefix -I,$(EXTRA_INCLUDES))
62
LDFLAGS += $(addprefix -L,$(EXTRA_LIBDIRS))
63 64
ifeq ($(ENABLE_PYTHON), 1)
	CFLAGS_ALL += $(shell python2.7-config --includes)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
65
	CXXFLAGS_ALL += $(shell python2.7-config --includes)
66
endif
67 68
ifeq ($(LUA_COMPILE),1)
	CFLAGS_ALL += -DLUA_COMPILE
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
69
	CXXFLAGS_ALL += -DLUA_COMPILE
70
endif
71 72 73 74 75 76 77

# Magic to track dependencies on header files. They are stored in the .d files
# by the compiler, then we load them on the next run and use them.
DEP_FILES := $(shell if test -d $(O)/.deps ; then find $(O)/.deps -name '*.d' ; fi | sort)
include $(DEP_FILES)

# Stuff to generate dependencies and link commands from the target_SOMETHING variables.
78
ifdef STATIC_LOCAL
79 80 81 82 83 84 85
LIB_SUFFIX :=.a
else
LIB_SUFFIX :=.so
endif

define COMMON_REGISTER

86
$(1): $$($(2)_EXTRA_DEPENDS)
87
$(1): $$(patsubst %,$(O)/.objs/$(3)%.o,$$($(2)_MODULES) $$($(2)_MODULES_3RDPARTY))
88
$(1): CFLAGS_ALL += $$($(2)_CFLAGS) $$(foreach CONFIG,$$($(2)_PKG_CONFIGS),$$(shell pkg-config --cflags $$(CONFIG))) $$(foreach CONFIG,$$($(2)_EXE_CONFIGS),$$(shell $$(CONFIG)-config --cflags))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
89
$(1): CXXFLAGS_ALL += $$($(2)_CXXFLAGS) $$(foreach CONFIG,$$($(2)_PKG_CONFIGS),$$(shell pkg-config --cflags $$(CONFIG))) $$(foreach CONFIG,$$($(2)_EXE_CONFIGS),$$(shell $$(CONFIG)-config --cflags))
90
$(1): LDFLAGS_ALL += $$($(2)_LDFLAGS) $$(foreach CONFIG,$$($(2)_PKG_CONFIGS),$$(shell pkg-config --libs $$(CONFIG))) $$(foreach CONFIG,$$($(2)_EXE_CONFIGS),$$(shell $$(CONFIG)-config --libs))
91 92 93 94 95 96
ifdef STATIC_GLOBAL
# TODO: The system libraries?
else
$(1): LINK_LIBRARIES += $$(addprefix -l,$$($(2)_SYSTEM_LIBS))
$(1): LINK_SO_LIBRARIES += $$(addprefix -l,$$($(2)_SO_LIBS))
endif
97 98 99 100 101
ifdef STATIC_LOCAL
$(1): LINK_LIBRARIES += $$(patsubst %,$(O)/lib/lib%.a,$$($(2)_LOCAL_LIBS))
$(1): $$(patsubst %,$(O)/lib/lib%.a,$$($(2)_LOCAL_LIBS))
else
$(1): LINK_LIBRARIES += -L$(O)/lib -Wl,-R$(abspath $(O)/lib) $$(addprefix -l,$$($(2)_LOCAL_LIBS))
102
$(1): $$(patsubst %,$(O)/lib/lib%.so,$$($(2)_LOCAL_LIBS))
103
endif
104

Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
105
cppcheck-$$(notdir $$(basename $(1))): $$(patsubst %,$(S)/$(3)%.$(LANG_MODE),$$(filter-out %.embed,$$($(2)_MODULES)))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
106

107 108 109 110 111 112 113 114 115
endef

# Function to register a binary to TARGETS and generate the rules to build it.
# It shall be called as:
#
# binary_name_MODULES := main other_file third_file
# $(eval $(call REGISTER_BIN,binary_name,src/path/to/directory))
define REGISTER_BIN

116
.PHONY: cppcheck cppcheck-all
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
117

118 119
ifneq (,$(findstring ^$(RESTRICT),^$(1)))
TARGETS += $(O)/$(1)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
120
cppcheck: cppcheck-$$(notdir $$(basename $(1)))
121
endif
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
122
cppcheck-all: cppcheck-$$(notdir $$(basename $(1)))
123 124 125 126 127 128 129 130
$(call COMMON_REGISTER,$(O)/bin/$$(notdir $(1)),$$(notdir $(1)),$$(dir $(1)))
$(O)/$(1): $(O)/bin/$$(notdir $(1))
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@

endef

131 132 133 134 135 136 137 138 139 140
define REGISTER_BINARY_NOTARGET

$(call COMMON_REGISTER,$(O)/bin/$$(notdir $(1)),$$(notdir $(1)),$$(dir $(1)))
$(O)/$(1): $(O)/bin/$$(notdir $(1))
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@

endef

141 142 143 144 145
# Similar, for libraries
define REGISTER_LIB

ifneq (,$(findstring ^$(RESTRICT),^$(1)))
TARGETS += $(O)/$(1)$(LIB_SUFFIX)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
146
cppcheck: cppcheck-$$(notdir $$(basename $(1)))
147
endif
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
148
cppcheck-all: cppcheck-$$(notdir $$(basename $(1)))
149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175
$(call COMMON_REGISTER,$(O)/lib/$$(notdir $(1)).a,$$(notdir $(1)),$$(dir $(1)))
$(call COMMON_REGISTER,$(O)/lib/$$(notdir $(1)).so,$$(notdir $(1)),$$(dir $(1)))
$(O)/$(1).a: $(O)/lib/$$(notdir $(1)).a
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@
$(O)/$(1).so: $(O)/lib/$$(notdir $(1)).so
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@

endef

# Similar, for documentation
define REGISTER_DOC

ifneq (,$(findstring ^$(RESTRICT),^$(1)))
TARGETS += $(O)/$(1).html
endif
$(O)/docs/$$(notdir $(1)).html: $(S)/$$(addsuffix .txt,$(1))
$(O)/$(1).html: $(O)/docs/$$(notdir $(1)).html
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@

endef

176 177 178 179 180 181 182 183 184
# For lua
define REGISTER_LUA

ifneq (,$(findstring ^$(RESTRICT),^$(1)))
TARGETS_LUA += $(O)/lua_lib/$(notdir $(1)).luac
endif
$(O)/lua_lib/$$(notdir $(1)).luac: $(S)/$$(addsuffix .lua,$(1))
endef

185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203
define REGISTER_SCRIPT

ifneq (,$(findstring ^$(RESTRICT),^$(1)))
TARGETS += $(O)/$(1)
endif

$(O)/$(1): $(O)/bin/$$(notdir $(1))
	$(M) LN $$@
	$(Q)mkdir -p $$(dir $(O)/$(1))
	$(Q)ln -sf $$(abspath $$<) $$@

$(O)/bin/$$(notdir $(1)): $(S)/$$(dir $(1))/$$($$(notdir $(1))_SOURCE)
	$(M) LN $$@
	$(Q)mkdir -p $(O)/bin/
	$(Q)ln -sf $$(abspath $$<) $$@

endef

# Generic rules to compile and link
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
204
$(O)/.objs/%.o: $(S)/%.$(LANG_MODE)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
205
	$(M) $(COMPILER) $@
206
	$(Q)mkdir -p $(dir $@ $(subst .objs/,.deps/,$@))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
207
	$(Q)$($(COMPILER)) $($(FLAGS)FLAGS_ALL) -c $< -o $@ -MD -MF $(patsubst %.o,%.pre,$(subst .objs/,.deps/,$@))
208 209
	$(Q)$(S)/build/normalize_dep_file.pl $(O) $(patsubst %.o,%.pre,$(subst .objs/,.deps/,$@)) >$(patsubst %.o,%.d,$(subst .objs/,.deps/,$@))

Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
210
$(O)/.objs/%.o: $(O)/.gen/%.$(LANG_MODE)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
211
	$(M) $(COMPILER) $@
212
	$(Q)mkdir -p $(dir $@ $(subst .objs/,.deps/,$@))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
213
	$(Q)$($(COMPILER)) $($(FLAGS)FLAGS_ALL) -c $< -o $@ -MD -MF $(patsubst %.o,%.pre,$(subst .objs/,.deps/,$@))
214 215
	$(Q)$(S)/build/normalize_dep_file.pl $(O) $(patsubst %.o,%.pre,$(subst .objs/,.deps/,$@)) >$(patsubst %.o,%.d,$(subst .objs/,.deps/,$@))

216
# Make sure the intermediate file is not deleted and more building is triggered
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
217
.PRECIOUS: $(O)/.gen/%.embed.$(LANG_MODE)
218

Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
219
$(O)/.gen/%.embed.$(LANG_MODE): $(O)/.gen/%.embedlist
220 221
	$(M) EMBED $@
	$(Q)mkdir -p $(dir $@ $(subst .gen/,.deps/,$@))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
222 223
	$(Q)$(S)/build/embed_gen.pl -i $< -o $@ -d $(patsubst %.$(LANG_MODE),%.pre,$(subst .gen/,.deps/,$@))
	$(Q)$(S)/build/normalize_dep_file.pl $(abspath $(O)) $(patsubst %.$(LANG_MODE),%.pre,$(subst .gen/,.deps/,$@)) >$(patsubst %.$(LANG_MODE),%.d,$(subst .gen/,.deps/,$@))
224

Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
225
$(O)/.gen/%.embed.$(LANG_MODE): $(S)/%.embedlist
226 227
	$(M) EMBED $@
	$(Q)mkdir -p $(dir $@ $(subst .gen/,.deps/,$@))
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
228 229
	$(Q)$(S)/build/embed_gen.pl -i $< -o $@ -d $(patsubst %.$(LANG_MODE),%.pre,$(subst .gen/,.deps/,$@))
	$(Q)$(S)/build/normalize_dep_file.pl $(abspath $(O)) $(patsubst %.$(LANG_MODE),%.pre,$(subst .gen/,.deps/,$@)) >$(patsubst %.$(LANG_MODE),%.d,$(subst .gen/,.deps/,$@))
230

231 232 233
$(O)/bin/%:
	$(M) LD $@
	$(Q)mkdir -p $(dir $@)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
234
	$(Q)$($(COMPILER)) $(filter %.o,$^) -o $@ $(LDFLAGS_ALL) $(LINK_LIBRARIES)
235 236 237 238 239 240 241

$(O)/lib/%.a:
	$(M) AR $@
	$(Q)mkdir -p $(dir $@)
	$(Q)$(AR) -rc $@ $(filter %.o,$^)

$(O)/lib/%.so: CFLAGS_ALL += -fPIC
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
242
$(O)/lib/%.so: CXXFLAGS_ALL += -fPIC
243 244 245
$(O)/lib/%.so:
	$(M) LD $@
	$(Q)mkdir -p $(dir $@)
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
246
	$(Q)$($(COMPILER)) -o $@ $(filter %.o,$^) $(LDFLAGS_ALL) $(LINK_SO_LIBRARIES) -shared
247 248 249 250 251

$(O)/docs/%:
	$(M) DOC-HTML $@
	$(Q)mkdir -p $(dir $@)
	$(Q)$(ASCIIDOC) -o $@ $<
252 253 254 255 256

$(O)/lua_lib/%:
	$(M) LUAC $@
	$(Q)mkdir -p $(dir $@)
	$(Q)$(LUAC) -o $@ $<
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
257

258 259 260 261 262 263
# An empty target without any prereqs. This one is „remade“ every time, triggering
# anything that depends on it, just like .PHONY. Except that it works well with
# generic/static rules.
FORCE:

cppcheck-%: FORCE
Michal 'vorner' Vaner's avatar
Michal 'vorner' Vaner committed
264
	$(M) CCPC $@
265
	$(Q)cppcheck --enable=style --enable=warning --std=$(subst gnu,c,$(STANDARD)) --suppress=allocaCalled --suppress=obsoleteFunctionsalloca --template='{file}:{line},{severity},{id},{message}' --inline-suppr --error-exitcode=1 -q $(filter-out FORCE,$^)