forked from Floorp-Projects/Floorp
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathrecurse.mk
219 lines (177 loc) · 8.39 KB
/
recurse.mk
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
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this file,
# You can obtain one at http://mozilla.org/MPL/2.0/.
ifndef INCLUDED_RULES_MK
include $(topsrcdir)/config/rules.mk
endif
# The traditional model of directory traversal with make is as follows:
# make -C foo
# Entering foo
# make -C bar
# Entering foo/bar
# make -C baz
# Entering foo/baz
# make -C qux
# Entering qux
#
# Pseudo derecurse transforms the above into:
# make -C foo
# make -C foo/bar
# make -C foo/baz
# make -C qux
# MOZ_PSEUDO_DERECURSE can have values other than 1.
ifeq (1_.,$(if $(MOZ_PSEUDO_DERECURSE),1)_$(DEPTH))
include root.mk
# Disable build status for mach in top directories without TIERS.
# In practice this disables it when recursing under js/src, which confuses mach.
ifndef TIERS
BUILDSTATUS =
endif
# Main rules (export, compile, binaries, libs and tools) call recurse_* rules.
# This wrapping is only really useful for build status.
compile binaries libs export tools::
$(call BUILDSTATUS,TIER_START $@ $($@_subtiers))
+$(MAKE) recurse_$@
$(call BUILDSTATUS,TIER_FINISH $@)
# Carefully avoid $(eval) type of rule generation, which makes pymake slower
# than necessary.
# Get current tier and corresponding subtiers from the data in root.mk.
CURRENT_TIER := $(filter $(foreach tier,compile binaries libs export tools,recurse_$(tier) $(tier)-deps),$(MAKECMDGOALS))
ifneq (,$(filter-out 0 1,$(words $(CURRENT_TIER))))
$(error $(CURRENT_TIER) not supported on the same make command line)
endif
CURRENT_TIER := $(subst recurse_,,$(CURRENT_TIER:-deps=))
CURRENT_SUBTIERS := $($(CURRENT_TIER)_subtiers)
# The rules here are doing directory traversal, so we don't want further
# recursion to happen when running make -C subdir $tier. But some make files
# further call make -C something else, and sometimes expect recursion to
# happen in that case (see browser/metro/locales/Makefile.in for example).
# Conveniently, every invocation of make increases MAKELEVEL, so only stop
# recursion from happening at current MAKELEVEL + 1.
ifdef CURRENT_TIER
ifeq (0,$(MAKELEVEL))
export NO_RECURSE_MAKELEVEL=1
else
export NO_RECURSE_MAKELEVEL=$(word $(MAKELEVEL),2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20)
endif
endif
# Get all directories traversed for all subtiers in the current tier, or use
# directly the $(*_dirs) variables available in root.mk when there is no
# TIERS (like for js/src).
CURRENT_DIRS := $(or $($(CURRENT_TIER)_dirs),$(foreach subtier,$(CURRENT_SUBTIERS),$($(CURRENT_TIER)_subtier_$(subtier))))
ifneq (,$(filter binaries libs,$(CURRENT_TIER)))
WANT_STAMPS = 1
STAMP_TOUCH = $(TOUCH) $(@D)/binaries
endif
# Subtier delimiter rules
$(addprefix subtiers/,$(addsuffix _start/$(CURRENT_TIER),$(CURRENT_SUBTIERS))): subtiers/%_start/$(CURRENT_TIER): $(if $(WANT_STAMPS),$(call mkdir_deps,subtiers/%_start))
$(call BUILDSTATUS,SUBTIER_START $(CURRENT_TIER) $* $(if $(BUG_915535_FIXED),$($(CURRENT_TIER)_subtier_$*)))
@$(STAMP_TOUCH)
$(addprefix subtiers/,$(addsuffix _finish/$(CURRENT_TIER),$(CURRENT_SUBTIERS))): subtiers/%_finish/$(CURRENT_TIER): $(if $(WANT_STAMPS),$(call mkdir_deps,subtiers/%_finish))
$(call BUILDSTATUS,SUBTIER_FINISH $(CURRENT_TIER) $*)
@$(STAMP_TOUCH)
$(addprefix subtiers/,$(addsuffix /$(CURRENT_TIER),$(CURRENT_SUBTIERS))): %/$(CURRENT_TIER): $(if $(WANT_STAMPS),$(call mkdir_deps,%))
@$(STAMP_TOUCH)
GARBAGE_DIRS += subtiers
# Recursion rule for all directories traversed for all subtiers in the
# current tier.
# root.mk defines subtier_of_* variables, that map a normalized subdir path to
# a subtier name (e.g. subtier_of_memory_jemalloc = base)
$(addsuffix /$(CURRENT_TIER),$(CURRENT_DIRS)): %/$(CURRENT_TIER):
ifdef BUG_915535_FIXED
$(call BUILDSTATUS,TIERDIR_START $(CURRENT_TIER) $(subtier_of_$(subst /,_,$*)) $*)
endif
+@$(MAKE) -C $* $(if $(filter $*,$(tier_$(subtier_of_$(subst /,_,$*))_staticdirs)),,$(CURRENT_TIER))
# Ensure existing stamps are up-to-date, but don't create one if submake didn't create one.
$(if $(wildcard $@),@$(STAMP_TOUCH))
ifdef BUG_915535_FIXED
$(call BUILDSTATUS,TIERDIR_FINISH $(CURRENT_TIER) $(subtier_of_$(subst /,_,$*)) $*)
endif
# Dummy rules for possibly inexisting dependencies for the above tier targets
$(addsuffix /Makefile,$(CURRENT_DIRS)) $(addsuffix /backend.mk,$(CURRENT_DIRS)):
# The export tier requires nsinstall, which is built from config. So every
# subdirectory traversal needs to happen after traversing config.
ifeq ($(CURRENT_TIER),export)
$(addsuffix /$(CURRENT_TIER),$(filter-out config,$(CURRENT_DIRS))): config/$(CURRENT_TIER)
endif
ifneq (,$(filter libs binaries,$(CURRENT_TIER)))
# When doing a "libs" build, target_libs.mk ensures the interesting dependency data
# is available in the "binaries" stamp. Once recursion is done, aggregate all that
# dependency info so that stamps depend on relevant files and relevant other stamps.
# When doing a "binaries" build, the aggregate dependency file and those stamps are
# used and allow to skip recursing directories where changes are not going to require
# rebuild. A few directories, however, are still traversed all the time, mostly, the
# gyp managed ones and js/src.
# A few things that are not traversed by a "binaries" build, but should, in an ideal
# world, are nspr, nss, icu and ffi.
recurse_$(CURRENT_TIER):
@$(MAKE) binaries-deps
# Creating binaries-deps.mk directly would make us build it twice: once when beginning
# the build because of the include, and once at the end because of the stamps.
binaries-deps: $(addsuffix /binaries,$(CURRENT_DIRS))
@$(call py_action,link_deps,-o $@.mk --group-by-depfile --topsrcdir $(topsrcdir) --topobjdir $(DEPTH) --dist $(DIST) --guard $(addprefix ",$(addsuffix ",$^)))
@$(TOUCH) $@
ifeq (recurse_binaries,$(MAKECMDGOALS))
$(call include_deps,binaries-deps.mk)
endif
endif
DIST_GARBAGE += binaries-deps.mk binaries-deps
else
# Don't recurse if MAKELEVEL is NO_RECURSE_MAKELEVEL as defined above, but
# still recurse for externally managed make files (gyp-generated ones).
ifeq ($(EXTERNALLY_MANAGED_MAKE_FILE)_$(NO_RECURSE_MAKELEVEL),_$(MAKELEVEL))
compile binaries libs export tools::
else
#########################
# Tier traversal handling
#########################
ifdef TIERS
libs export tools::
$(call BUILDSTATUS,TIER_START $@ $(filter-out $(if $(filter export,$@),,precompile),$(TIERS)))
$(foreach tier,$(TIERS), $(if $(filter-out libs_precompile tools_precompile,$@_$(tier)), \
$(call BUILDSTATUS,SUBTIER_START $@ $(tier) $(if $(filter libs,$@),$(tier_$(tier)_staticdirs)) $(tier_$(tier)_dirs)) \
$(if $(filter libs,$@),$(foreach dir, $(tier_$(tier)_staticdirs), $(call TIER_DIR_SUBMAKE,$@,$(tier),$(dir),,1))) \
$(foreach dir, $(tier_$(tier)_dirs), $(call TIER_DIR_SUBMAKE,$@,$(tier),$(dir),$@)) \
$(call BUILDSTATUS,SUBTIER_FINISH $@ $(tier))))
$(call BUILDSTATUS,TIER_FINISH $@)
else
define CREATE_SUBTIER_TRAVERSAL_RULE
PARALLEL_DIRS_$(1) = $$(addsuffix _$(1),$$(PARALLEL_DIRS))
.PHONY: $(1) $$(PARALLEL_DIRS_$(1))
ifdef PARALLEL_DIRS
$$(PARALLEL_DIRS_$(1)): %_$(1): %/Makefile
+@$$(call SUBMAKE,$(1),$$*)
endif
$(1):: $$(SUBMAKEFILES)
ifdef PARALLEL_DIRS
+@$(MAKE) $$(PARALLEL_DIRS_$(1))
endif
$$(LOOP_OVER_DIRS)
endef
$(foreach subtier,export compile binaries libs tools,$(eval $(call CREATE_SUBTIER_TRAVERSAL_RULE,$(subtier))))
tools export:: $(SUBMAKEFILES)
$(LOOP_OVER_TOOL_DIRS)
endif # ifdef TIERS
endif # ifeq ($(EXTERNALLY_MANAGED_MAKE_FILE)_$(NO_RECURSE_MAKELEVEL),_$(MAKELEVEL))
endif # ifeq (1_.,$(MOZ_PSEUDO_DERECURSE)_$(DEPTH))
ifdef MOZ_PSEUDO_DERECURSE
ifdef EXTERNALLY_MANAGED_MAKE_FILE
# gyp-managed directories
recurse_targets := $(addsuffix /binaries,$(DIRS) $(PARALLEL_DIRS))
else
ifeq (.,$(DEPTH))
# top-level directories
recurse_targets := $(addsuffix /binaries,$(binaries_dirs))
ifdef recurse_targets
# only js/src has binaries_dirs, and we want to adjust paths for it.
want_abspaths = 1
endif
endif
endif
binaries libs:: $(TARGETS) $(BINARIES_PP)
# Aggregate all dependency files relevant to a binaries build except in
# the mozilla top-level directory.
ifneq (_.,$(recurse_targets)_$(DEPTH))
@$(if $(or $(recurse_targets),$^),$(call py_action,link_deps,-o binaries --group-all $(if $(want_abspaths),--abspaths )--topsrcdir $(topsrcdir) --topobjdir $(DEPTH) --dist $(DIST) $(BINARIES_PP) $(wildcard $(addsuffix .pp,$(addprefix $(MDDEPDIR)/,$(notdir $(sort $(filter-out $(BINARIES_PP),$^) $(OBJ_TARGETS)))))) $(recurse_targets)))
endif
endif # ifdef MOZ_PSEUDO_DERECURSE