1define int_vars
2#Set defaults for vars which may be overridden per-package
3$(1)_cc=$($($(1)_type)_CC)
4$(1)_cxx=$($($(1)_type)_CXX)
5$(1)_objc=$($($(1)_type)_OBJC)
6$(1)_objcxx=$($($(1)_type)_OBJCXX)
7$(1)_ar=$($($(1)_type)_AR)
8$(1)_ranlib=$($($(1)_type)_RANLIB)
9$(1)_libtool=$($($(1)_type)_LIBTOOL)
10$(1)_nm=$($($(1)_type)_NM)
11$(1)_cflags=$($($(1)_type)_CFLAGS) $($($(1)_type)_$(release_type)_CFLAGS)
12$(1)_cxxflags=$($($(1)_type)_CXXFLAGS) $($($(1)_type)_$(release_type)_CXXFLAGS)
13$(1)_ldflags=$($($(1)_type)_LDFLAGS) $($($(1)_type)_$(release_type)_LDFLAGS) -L$($($(1)_type)_prefix)/lib
14$(1)_cppflags=$($($(1)_type)_CPPFLAGS) $($($(1)_type)_$(release_type)_CPPFLAGS) -I$($($(1)_type)_prefix)/include
15$(1)_recipe_hash:=
16endef
17
18define int_get_all_dependencies
19$(sort $(foreach dep,$(2),$(2) $(call int_get_all_dependencies,$(1),$($(dep)_dependencies))))
20endef
21
22define fetch_file_inner
23    ( mkdir -p $$($(1)_download_dir) && echo Fetching $(3) from $(2) && \
24    $(build_DOWNLOAD) "$$($(1)_download_dir)/$(4).temp" "$(2)/$(3)" && \
25    echo "$(5)  $$($(1)_download_dir)/$(4).temp" > $$($(1)_download_dir)/.$(4).hash && \
26    $(build_SHA256SUM) -c $$($(1)_download_dir)/.$(4).hash && \
27    mv $$($(1)_download_dir)/$(4).temp $$($(1)_source_dir)/$(4) && \
28    rm -rf $$($(1)_download_dir) )
29endef
30
31define fetch_file
32    ( test -f $$($(1)_source_dir)/$(4) || \
33    ( $(call fetch_file_inner,$(1),$(2),$(3),$(4),$(5)) || \
34      $(call fetch_file_inner,$(1),$(FALLBACK_DOWNLOAD_PATH),$(3),$(4),$(5))))
35endef
36
37define int_get_build_recipe_hash
38$(eval $(1)_all_file_checksums:=$(shell $(build_SHA256SUM) $(meta_depends) packages/$(1).mk $(addprefix $(PATCHES_PATH)/$(1)/,$($(1)_patches)) | cut -d" " -f1))
39$(eval $(1)_recipe_hash:=$(shell echo -n "$($(1)_all_file_checksums)" | $(build_SHA256SUM) | cut -d" " -f1))
40endef
41
42define int_get_build_id
43$(eval $(1)_dependencies += $($(1)_$(host_arch)_$(host_os)_dependencies) $($(1)_$(host_os)_dependencies))
44$(eval $(1)_all_dependencies:=$(call int_get_all_dependencies,$(1),$($($(1)_type)_native_toolchain) $($($(1)_type)_native_binutils) $($(1)_dependencies)))
45$(foreach dep,$($(1)_all_dependencies),$(eval $(1)_build_id_deps+=$(dep)-$($(dep)_version)-$($(dep)_recipe_hash)))
46$(eval $(1)_build_id_long:=$(1)-$($(1)_version)-$($(1)_recipe_hash)-$(release_type) $($(1)_build_id_deps) $($($(1)_type)_id_string))
47$(eval $(1)_build_id:=$(shell echo -n "$($(1)_build_id_long)" | $(build_SHA256SUM) | cut -c-$(HASH_LENGTH)))
48final_build_id_long+=$($(package)_build_id_long)
49
50#compute package-specific paths
51$(1)_build_subdir?=.
52$(1)_download_file?=$($(1)_file_name)
53$(1)_source_dir:=$(SOURCES_PATH)
54$(1)_source:=$$($(1)_source_dir)/$($(1)_file_name)
55$(1)_staging_dir=$(base_staging_dir)/$(host)/$(1)/$($(1)_version)-$($(1)_build_id)
56$(1)_staging_prefix_dir:=$$($(1)_staging_dir)$($($(1)_type)_prefix)
57$(1)_extract_dir:=$(base_build_dir)/$(host)/$(1)/$($(1)_version)-$($(1)_build_id)
58$(1)_download_dir:=$(base_download_dir)/$(1)-$($(1)_version)
59$(1)_build_dir:=$$($(1)_extract_dir)/$$($(1)_build_subdir)
60$(1)_cached_checksum:=$(BASE_CACHE)/$(host)/$(1)/$(1)-$($(1)_version)-$($(1)_build_id).tar.gz.hash
61$(1)_patch_dir:=$(base_build_dir)/$(host)/$(1)/$($(1)_version)-$($(1)_build_id)/.patches-$($(1)_build_id)
62$(1)_prefixbin:=$($($(1)_type)_prefix)/bin/
63$(1)_cached:=$(BASE_CACHE)/$(host)/$(1)/$(1)-$($(1)_version)-$($(1)_build_id).tar.gz
64$(1)_all_sources=$($(1)_file_name) $($(1)_extra_sources)
65
66#stamps
67$(1)_fetched=$(SOURCES_PATH)/download-stamps/.stamp_fetched-$(1)-$($(1)_file_name).hash
68$(1)_extracted=$$($(1)_extract_dir)/.stamp_extracted
69$(1)_preprocessed=$$($(1)_extract_dir)/.stamp_preprocessed
70$(1)_cleaned=$$($(1)_extract_dir)/.stamp_cleaned
71$(1)_built=$$($(1)_build_dir)/.stamp_built
72$(1)_configured=$$($(1)_build_dir)/.stamp_configured
73$(1)_staged=$$($(1)_staging_dir)/.stamp_staged
74$(1)_postprocessed=$$($(1)_staging_prefix_dir)/.stamp_postprocessed
75$(1)_download_path_fixed=$(subst :,\:,$$($(1)_download_path))
76
77
78#default commands
79# The default behavior for tar will try to set ownership when running as uid 0 and may not succeed, --no-same-owner disables this behavior
80$(1)_fetch_cmds ?= $(call fetch_file,$(1),$(subst \:,:,$$($(1)_download_path_fixed)),$$($(1)_download_file),$($(1)_file_name),$($(1)_sha256_hash))
81$(1)_extract_cmds ?= mkdir -p $$($(1)_extract_dir) && echo "$$($(1)_sha256_hash)  $$($(1)_source)" > $$($(1)_extract_dir)/.$$($(1)_file_name).hash &&  $(build_SHA256SUM) -c $$($(1)_extract_dir)/.$$($(1)_file_name).hash && tar --no-same-owner --strip-components=1 -xf $$($(1)_source)
82$(1)_preprocess_cmds ?=
83$(1)_build_cmds ?=
84$(1)_config_cmds ?=
85$(1)_stage_cmds ?=
86$(1)_set_vars ?=
87
88
89all_sources+=$$($(1)_fetched)
90endef
91#$(foreach dep_target,$($(1)_all_dependencies),$(eval $(1)_dependency_targets=$($(dep_target)_cached)))
92
93
94define int_config_attach_build_config
95$(eval $(call $(1)_set_vars,$(1)))
96$(1)_cflags+=$($(1)_cflags_$(release_type))
97$(1)_cflags+=$($(1)_cflags_$(host_arch)) $($(1)_cflags_$(host_arch)_$(release_type))
98$(1)_cflags+=$($(1)_cflags_$(host_os)) $($(1)_cflags_$(host_os)_$(release_type))
99$(1)_cflags+=$($(1)_cflags_$(host_arch)_$(host_os)) $($(1)_cflags_$(host_arch)_$(host_os)_$(release_type))
100
101$(1)_cxxflags+=$($(1)_cxxflags_$(release_type))
102$(1)_cxxflags+=$($(1)_cxxflags_$(host_arch)) $($(1)_cxxflags_$(host_arch)_$(release_type))
103$(1)_cxxflags+=$($(1)_cxxflags_$(host_os)) $($(1)_cxxflags_$(host_os)_$(release_type))
104$(1)_cxxflags+=$($(1)_cxxflags_$(host_arch)_$(host_os)) $($(1)_cxxflags_$(host_arch)_$(host_os)_$(release_type))
105
106$(1)_cppflags+=$($(1)_cppflags_$(release_type))
107$(1)_cppflags+=$($(1)_cppflags_$(host_arch)) $($(1)_cppflags_$(host_arch)_$(release_type))
108$(1)_cppflags+=$($(1)_cppflags_$(host_os)) $($(1)_cppflags_$(host_os)_$(release_type))
109$(1)_cppflags+=$($(1)_cppflags_$(host_arch)_$(host_os)) $($(1)_cppflags_$(host_arch)_$(host_os)_$(release_type))
110
111$(1)_ldflags+=$($(1)_ldflags_$(release_type))
112$(1)_ldflags+=$($(1)_ldflags_$(host_arch)) $($(1)_ldflags_$(host_arch)_$(release_type))
113$(1)_ldflags+=$($(1)_ldflags_$(host_os)) $($(1)_ldflags_$(host_os)_$(release_type))
114$(1)_ldflags+=$($(1)_ldflags_$(host_arch)_$(host_os)) $($(1)_ldflags_$(host_arch)_$(host_os)_$(release_type))
115
116$(1)_build_opts+=$$($(1)_build_opts_$(release_type))
117$(1)_build_opts+=$$($(1)_build_opts_$(host_arch)) $$($(1)_build_opts_$(host_arch)_$(release_type))
118$(1)_build_opts+=$$($(1)_build_opts_$(host_os)) $$($(1)_build_opts_$(host_os)_$(release_type))
119$(1)_build_opts+=$$($(1)_build_opts_$(host_arch)_$(host_os)) $$($(1)_build_opts_$(host_arch)_$(host_os)_$(release_type))
120
121$(1)_config_opts+=$$($(1)_config_opts_$(release_type))
122$(1)_config_opts+=$$($(1)_config_opts_$(host_arch)) $$($(1)_config_opts_$(host_arch)_$(release_type))
123$(1)_config_opts+=$$($(1)_config_opts_$(host_os)) $$($(1)_config_opts_$(host_os)_$(release_type))
124$(1)_config_opts+=$$($(1)_config_opts_$(host_arch)_$(host_os)) $$($(1)_config_opts_$(host_arch)_$(host_os)_$(release_type))
125
126$(1)_config_env+=$$($(1)_config_env_$(release_type))
127$(1)_config_env+=$($(1)_config_env_$(host_arch)) $($(1)_config_env_$(host_arch)_$(release_type))
128$(1)_config_env+=$($(1)_config_env_$(host_os)) $($(1)_config_env_$(host_os)_$(release_type))
129$(1)_config_env+=$($(1)_config_env_$(host_arch)_$(host_os)) $($(1)_config_env_$(host_arch)_$(host_os)_$(release_type))
130
131$(1)_config_env+=PKG_CONFIG_LIBDIR=$($($(1)_type)_prefix)/lib/pkgconfig
132$(1)_config_env+=PKG_CONFIG_PATH=$($($(1)_type)_prefix)/share/pkgconfig
133$(1)_config_env+=CMAKE_MODULE_PATH=$($($(1)_type)_prefix)/lib/cmake
134$(1)_config_env+=PATH=$(build_prefix)/bin:$(PATH)
135$(1)_build_env+=PATH=$(build_prefix)/bin:$(PATH)
136$(1)_stage_env+=PATH=$(build_prefix)/bin:$(PATH)
137$(1)_autoconf=./configure --host=$($($(1)_type)_host) --prefix=$($($(1)_type)_prefix) $$($(1)_config_opts) CC="$$($(1)_cc)" CXX="$$($(1)_cxx)"
138ifneq ($($(1)_nm),)
139$(1)_autoconf += NM="$$($(1)_nm)"
140endif
141ifneq ($($(1)_ranlib),)
142$(1)_autoconf += RANLIB="$$($(1)_ranlib)"
143endif
144ifneq ($($(1)_ar),)
145$(1)_autoconf += AR="$$($(1)_ar)"
146endif
147ifneq ($($(1)_cflags),)
148$(1)_autoconf += CFLAGS="$$($(1)_cflags)"
149endif
150ifneq ($($(1)_cxxflags),)
151$(1)_autoconf += CXXFLAGS="$$($(1)_cxxflags)"
152endif
153ifneq ($($(1)_cppflags),)
154$(1)_autoconf += CPPFLAGS="$$($(1)_cppflags)"
155endif
156ifneq ($($(1)_ldflags),)
157$(1)_autoconf += LDFLAGS="$$($(1)_ldflags)"
158endif
159
160$(1)_cmake=env CC="$$($(1)_cc)" \
161               CFLAGS="$$($(1)_cppflags) $$($(1)_cflags)" \
162               CXX="$$($(1)_cxx)" \
163               CXXFLAGS="$$($(1)_cppflags) $$($(1)_cxxflags)" \
164               LDFLAGS="$$($(1)_ldflags)" \
165             cmake -DCMAKE_INSTALL_PREFIX:PATH="$$($($(1)_type)_prefix)"
166ifneq ($($(1)_type),build)
167ifneq ($(host),$(build))
168$(1)_cmake += -DCMAKE_SYSTEM_NAME=$($(host_os)_cmake_system)
169$(1)_cmake += -DCMAKE_C_COMPILER_TARGET=$(host)
170$(1)_cmake += -DCMAKE_CXX_COMPILER_TARGET=$(host)
171endif
172endif
173endef
174
175define int_add_cmds
176$($(1)_fetched):
177	$(AT)mkdir -p $$(@D) $(SOURCES_PATH)
178	$(AT)rm -f $$@
179	$(AT)touch $$@
180	$(AT)cd $$(@D); $(call $(1)_fetch_cmds,$(1))
181	$(AT)cd $($(1)_source_dir); $(foreach source,$($(1)_all_sources),$(build_SHA256SUM) $(source) >> $$(@);)
182	$(AT)touch $$@
183$($(1)_extracted): | $($(1)_fetched)
184	$(AT)echo Extracting $(1)...
185	$(AT)mkdir -p $$(@D)
186	$(AT)cd $$(@D); $(call $(1)_extract_cmds,$(1))
187	$(AT)touch $$@
188$($(1)_preprocessed): | $($(1)_extracted)
189	$(AT)echo Preprocessing $(1)...
190	$(AT)mkdir -p $$(@D) $($(1)_patch_dir)
191	$(AT)$(foreach patch,$($(1)_patches),cd $(PATCHES_PATH)/$(1); cp $(patch) $($(1)_patch_dir) ;)
192	$(AT)cd $$(@D); $(call $(1)_preprocess_cmds, $(1))
193	$(AT)touch $$@
194$($(1)_configured): | $($(1)_dependencies) $($(1)_preprocessed)
195	$(AT)echo Configuring $(1)...
196	$(AT)rm -rf $(host_prefix); mkdir -p $(host_prefix)/lib; cd $(host_prefix); $(foreach package,$($(1)_all_dependencies), tar --no-same-owner -xf $($(package)_cached); )
197	$(AT)mkdir -p $$(@D)
198	$(AT)+cd $$(@D); $($(1)_config_env) $(call $(1)_config_cmds, $(1))
199	$(AT)touch $$@
200$($(1)_built): | $($(1)_configured)
201	$(AT)echo Building $(1)...
202	$(AT)mkdir -p $$(@D)
203	$(AT)+cd $$(@D); $($(1)_build_env) $(call $(1)_build_cmds, $(1))
204	$(AT)touch $$@
205$($(1)_staged): | $($(1)_built)
206	$(AT)echo Staging $(1)...
207	$(AT)mkdir -p $($(1)_staging_dir)/$(host_prefix)
208	$(AT)cd $($(1)_build_dir); $($(1)_stage_env) $(call $(1)_stage_cmds, $(1))
209	$(AT)rm -rf $($(1)_extract_dir)
210	$(AT)touch $$@
211$($(1)_postprocessed): | $($(1)_staged)
212	$(AT)echo Postprocessing $(1)...
213	$(AT)cd $($(1)_staging_prefix_dir); $(call $(1)_postprocess_cmds)
214	$(AT)touch $$@
215$($(1)_cached): | $($(1)_dependencies) $($(1)_postprocessed)
216	$(AT)echo Caching $(1)...
217	$(AT)cd $$($(1)_staging_dir)/$(host_prefix); find . | sort | tar --no-recursion -czf $$($(1)_staging_dir)/$$(@F) -T -
218	$(AT)mkdir -p $$(@D)
219	$(AT)rm -rf $$(@D) && mkdir -p $$(@D)
220	$(AT)mv $$($(1)_staging_dir)/$$(@F) $$(@)
221	$(AT)rm -rf $($(1)_staging_dir)
222$($(1)_cached_checksum): $($(1)_cached)
223	$(AT)cd $$(@D); $(build_SHA256SUM) $$(<F) > $$(@)
224
225.PHONY: $(1)
226$(1): | $($(1)_cached_checksum)
227.SECONDARY: $($(1)_cached) $($(1)_postprocessed) $($(1)_staged) $($(1)_built) $($(1)_configured) $($(1)_preprocessed) $($(1)_extracted) $($(1)_fetched)
228
229endef
230
231stages = fetched extracted preprocessed configured built staged postprocessed cached cached_checksum
232
233define ext_add_stages
234$(foreach stage,$(stages),
235          $(1)_$(stage): $($(1)_$(stage))
236          .PHONY: $(1)_$(stage))
237endef
238
239# These functions create the build targets for each package. They must be
240# broken down into small steps so that each part is done for all packages
241# before moving on to the next step. Otherwise, a package's info
242# (build-id for example) would only be available to another package if it
243# happened to be computed already.
244
245#set the type for host/build packages.
246$(foreach native_package,$(native_packages),$(eval $(native_package)_type=build))
247$(foreach package,$(packages),$(eval $(package)_type=$(host_arch)_$(host_os)))
248
249#set overridable defaults
250$(foreach package,$(all_packages),$(eval $(call int_vars,$(package))))
251
252#include package files
253$(foreach package,$(all_packages),$(eval include packages/$(package).mk))
254
255#compute a hash of all files that comprise this package's build recipe
256$(foreach package,$(all_packages),$(eval $(call int_get_build_recipe_hash,$(package))))
257
258#generate a unique id for this package, incorporating its dependencies as well
259$(foreach package,$(all_packages),$(eval $(call int_get_build_id,$(package))))
260
261#compute final vars after reading package vars
262$(foreach package,$(all_packages),$(eval $(call int_config_attach_build_config,$(package))))
263
264#create build targets
265$(foreach package,$(all_packages),$(eval $(call int_add_cmds,$(package))))
266
267#special exception: if a toolchain package exists, all non-native packages depend on it
268$(foreach package,$(packages),$(eval $($(package)_extracted): |$($($(host_arch)_$(host_os)_native_toolchain)_cached) $($($(host_arch)_$(host_os)_native_binutils)_cached) ))
269