You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

485 lines
16KB

  1. # -*- makefile -*-
  2. # vim:set ts=8 sw=8 sts=8 noet:
  3. # This Source Code Form is subject to the terms of the Mozilla Public
  4. # License, v. 2.0. If a copy of the MPL was not distributed with this
  5. # file, You can obtain one at http://mozilla.org/MPL/2.0/.
  6. # Build a UXP application.
  7. #
  8. # To build a tree,
  9. # 1. git clone https://url.of/repo.git name-of-source-directory
  10. # 2. cd name-of-source-directory
  11. # 3. git submodule init && git submodule update
  12. # 4. create your .mozconfig file
  13. # 5. (g|moz)make -f client.mk or use mach
  14. #
  15. # Other targets ((g|moz)make -f client.mk [targets...]),
  16. # build
  17. # clean (realclean is now the same as clean)
  18. # distclean
  19. #
  20. # See relevant build documention for more information.
  21. #
  22. # Options:
  23. # MOZ_BUILD_PROJECTS - Build multiple projects in subdirectories
  24. # of MOZ_OBJDIR
  25. # MOZ_OBJDIR - Destination object directory
  26. # MOZ_MAKE_FLAGS - Flags to pass to $(MAKE)
  27. # MOZ_PREFLIGHT_ALL } - Makefiles to run before any project in
  28. # MOZ_PREFLIGHT } MOZ_BUILD_PROJECTS, before each project, after
  29. # MOZ_POSTFLIGHT } each project, and after all projects; these
  30. # MOZ_POSTFLIGHT_ALL } variables contain space-separated lists
  31. # MOZ_UNIFY_BDATE - Set to use the same bdate for each project in
  32. # MOZ_BUILD_PROJECTS
  33. #
  34. #######################################################################
  35. # Defines
  36. comma := ,
  37. ifdef MACH
  38. ifndef NO_BUILDSTATUS_MESSAGES
  39. define BUILDSTATUS
  40. @echo 'BUILDSTATUS $1'
  41. endef
  42. endif
  43. endif
  44. CWD := $(CURDIR)
  45. ifneq (1,$(words $(CWD)))
  46. $(error The platform directory cannot be located in a path with spaces.)
  47. endif
  48. ifeq "$(CWD)" "/"
  49. CWD := /.
  50. endif
  51. ifndef TOPSRCDIR
  52. ifeq (,$(wildcard client.mk))
  53. TOPSRCDIR := $(patsubst %/,%,$(dir $(MAKEFILE_LIST)))
  54. else
  55. TOPSRCDIR := $(CWD)
  56. endif
  57. endif
  58. SH := /bin/sh
  59. PERL ?= perl
  60. PYTHON ?= $(shell which python2.7 > /dev/null 2>&1 && echo python2.7 || echo python)
  61. CONFIG_GUESS_SCRIPT := $(wildcard $(TOPSRCDIR)/platform/build/autoconf/config.guess)
  62. ifdef CONFIG_GUESS_SCRIPT
  63. CONFIG_GUESS := $(shell $(CONFIG_GUESS_SCRIPT))
  64. endif
  65. ####################################
  66. # Sanity checks
  67. # Windows checks.
  68. ifneq (,$(findstring mingw,$(CONFIG_GUESS)))
  69. # check for CRLF line endings
  70. ifneq (0,$(shell $(PERL) -e 'binmode(STDIN); while (<STDIN>) { if (/\r/) { print "1"; exit } } print "0"' < $(TOPSRCDIR)/client.mk))
  71. $(error This source tree appears to have Windows-style line endings. Please convert it to Unix-style line endings.)
  72. endif
  73. endif
  74. ####################################
  75. # Load mozconfig Options
  76. # See relevant build pages for how to set up mozconfig.
  77. define CR
  78. endef
  79. # As $(shell) doesn't preserve newlines, use sed to replace them with an
  80. # unlikely sequence (||), which is then replaced back to newlines by make
  81. # before evaluation. $(shell) replacing newlines with spaces, || is always
  82. # followed by a space (since sed doesn't remove newlines), except on the
  83. # last line, so replace both '|| ' and '||'.
  84. # Also, make MOZ_PGO available to mozconfig when passed on make command line.
  85. # Likewise for MOZ_CURRENT_PROJECT.
  86. MOZCONFIG_CONTENT := $(subst ||,$(CR),$(subst || ,$(CR),$(shell $(addprefix MOZ_CURRENT_PROJECT=,$(MOZ_CURRENT_PROJECT)) MOZ_PGO=$(MOZ_PGO) $(TOPSRCDIR)/mach environment --format=client.mk | sed 's/$$/||/')))
  87. $(eval $(MOZCONFIG_CONTENT))
  88. export FOUND_MOZCONFIG
  89. # As '||' was used as a newline separator, it means it's not occurring in
  90. # lines themselves. It can thus safely be used to replaces normal spaces,
  91. # to then replace newlines with normal spaces. This allows to get a list
  92. # of mozconfig output lines.
  93. MOZCONFIG_OUT_LINES := $(subst $(CR), ,$(subst $(NULL) $(NULL),||,$(MOZCONFIG_CONTENT)))
  94. # Filter-out comments from those lines.
  95. START_COMMENT = \#
  96. MOZCONFIG_OUT_FILTERED := $(filter-out $(START_COMMENT)%,$(MOZCONFIG_OUT_LINES))
  97. ifdef AUTOCLOBBER
  98. export AUTOCLOBBER=1
  99. endif
  100. ifdef MOZ_PGO
  101. export MOZ_PGO
  102. endif
  103. ifdef MOZ_PARALLEL_BUILD
  104. MOZ_MAKE_FLAGS := $(filter-out -j%,$(MOZ_MAKE_FLAGS))
  105. MOZ_MAKE_FLAGS += -j$(MOZ_PARALLEL_BUILD)
  106. endif
  107. # Automatically add -jN to make flags if not defined. N defaults to number of cores.
  108. ifeq (,$(findstring -j,$(MOZ_MAKE_FLAGS)))
  109. cores=$(shell $(PYTHON) -c 'import multiprocessing; print(multiprocessing.cpu_count())')
  110. MOZ_MAKE_FLAGS += -j$(cores)
  111. endif
  112. ifdef MOZ_BUILD_PROJECTS
  113. ifdef MOZ_CURRENT_PROJECT
  114. BUILD_PROJECT_ARG = MOZ_BUILD_APP=$(MOZ_CURRENT_PROJECT)
  115. export MOZ_CURRENT_PROJECT
  116. else
  117. MOZ_MAKE = $(error Cannot build in the OBJDIR when MOZ_CURRENT_PROJECT is not set.)
  118. endif
  119. endif # MOZ_BUILD_PROJECTS
  120. MOZ_MAKE = $(MAKE) $(MOZ_MAKE_FLAGS) -C $(OBJDIR)
  121. # 'configure' scripts generated by autoconf.
  122. CONFIGURES := $(TOPSRCDIR)/configure
  123. CONFIGURES += $(TOPSRCDIR)/platform/configure
  124. CONFIGURES += $(TOPSRCDIR)/platform/js/src/configure
  125. # Make targets that are going to be passed to the real build system
  126. OBJDIR_TARGETS = install export libs clean realclean distclean maybe_clobber_profiledbuild upload sdk installer package package-compare stage-package source-package l10n-check automation/build
  127. #######################################################################
  128. # Rules
  129. # The default rule is build
  130. build::
  131. $(MAKE) -f $(TOPSRCDIR)/client.mk $(if $(MOZ_PGO),profiledbuild,realbuild) CREATE_MOZCONFIG_JSON=
  132. # Define mkdir
  133. include $(TOPSRCDIR)/config/makefiles/makeutils.mk
  134. include $(TOPSRCDIR)/config/makefiles/autotargets.mk
  135. # Create a makefile containing the mk_add_options values from mozconfig,
  136. # but only do so when OBJDIR is defined (see further above).
  137. ifdef MOZ_BUILD_PROJECTS
  138. ifdef MOZ_CURRENT_PROJECT
  139. WANT_MOZCONFIG_MK = 1
  140. else
  141. WANT_MOZCONFIG_MK =
  142. endif
  143. else
  144. WANT_MOZCONFIG_MK = 1
  145. endif
  146. ifdef WANT_MOZCONFIG_MK
  147. # For now, only output "export" lines and lines containing UPLOAD_EXTRA_FILES
  148. # from mach environment --format=client.mk output.
  149. MOZCONFIG_MK_LINES := $(filter export||% UPLOAD_EXTRA_FILES% %UPLOAD_EXTRA_FILES%,$(MOZCONFIG_OUT_LINES))
  150. $(OBJDIR)/.mozconfig.mk: $(TOPSRCDIR)/client.mk $(FOUND_MOZCONFIG) $(call mkdir_deps,$(OBJDIR)) $(OBJDIR)/CLOBBER
  151. $(if $(MOZCONFIG_MK_LINES),( $(foreach line,$(MOZCONFIG_MK_LINES), echo '$(subst ||, ,$(line))';) )) > $@
  152. ifdef MOZ_CURRENT_PROJECT
  153. echo export MOZ_CURRENT_PROJECT=$(MOZ_CURRENT_PROJECT) >> $@
  154. endif
  155. # Include that makefile so that it is created. This should not actually change
  156. # the environment since MOZCONFIG_CONTENT, which MOZCONFIG_OUT_LINES derives
  157. # from, has already been eval'ed.
  158. include $(OBJDIR)/.mozconfig.mk
  159. endif
  160. # Print out any options loaded from mozconfig.
  161. all realbuild clean distclean export libs install realclean::
  162. ifneq (,$(strip $(MOZCONFIG_OUT_FILTERED)))
  163. $(info Adding client.mk options from $(FOUND_MOZCONFIG):)
  164. $(foreach line,$(MOZCONFIG_OUT_FILTERED),$(info $(NULL) $(NULL) $(NULL) $(NULL) $(subst ||, ,$(line))))
  165. endif
  166. # Windows equivalents
  167. build_all: build
  168. clobber clobber_all: clean
  169. # helper target for mobile
  170. build_and_deploy: build package install
  171. # Do everything from scratch
  172. everything: clean build
  173. ####################################
  174. # Profile-Guided Optimization
  175. # This is up here, outside of the MOZ_CURRENT_PROJECT logic so that this
  176. # is usable in multi-pass builds, where you might not have a runnable
  177. # application until all the build passes and postflight scripts have run.
  178. profiledbuild::
  179. $(call BUILDSTATUS,TIERS pgo_profile_generate pgo_package pgo_profile pgo_clobber pgo_profile_use)
  180. $(call BUILDSTATUS,TIER_START pgo_profile_generate)
  181. $(MAKE) -f $(TOPSRCDIR)/client.mk realbuild MOZ_PROFILE_GENERATE=1 MOZ_PGO_INSTRUMENTED=1 CREATE_MOZCONFIG_JSON=
  182. $(call BUILDSTATUS,TIER_FINISH pgo_profile_generate)
  183. $(call BUILDSTATUS,TIER_START pgo_package)
  184. $(MAKE) -C $(OBJDIR) package MOZ_PGO_INSTRUMENTED=1 MOZ_INTERNAL_SIGNING_FORMAT= MOZ_EXTERNAL_SIGNING_FORMAT=
  185. rm -f $(OBJDIR)/jarlog/en-US.log
  186. $(call BUILDSTATUS,TIER_FINISH pgo_package)
  187. $(call BUILDSTATUS,TIER_START pgo_profile)
  188. MOZ_PGO_INSTRUMENTED=1 JARLOG_FILE=jarlog/en-US.log EXTRA_TEST_ARGS=10 $(MAKE) -C $(OBJDIR) pgo-profile-run
  189. $(call BUILDSTATUS,TIER_FINISH pgo_profile)
  190. $(call BUILDSTATUS,TIER_START pgo_clobber)
  191. $(MAKE) -f $(TOPSRCDIR)/client.mk maybe_clobber_profiledbuild CREATE_MOZCONFIG_JSON=
  192. $(call BUILDSTATUS,TIER_FINISH pgo_clobber)
  193. $(call BUILDSTATUS,TIER_START pgo_profile_use)
  194. $(MAKE) -f $(TOPSRCDIR)/client.mk realbuild MOZ_PROFILE_USE=1 CREATE_MOZCONFIG_JSON=
  195. $(call BUILDSTATUS,TIER_FINISH pgo_profile_use)
  196. #####################################################
  197. # Build date unification
  198. ifdef MOZ_UNIFY_BDATE
  199. ifndef MOZ_BUILD_DATE
  200. ifdef MOZ_BUILD_PROJECTS
  201. MOZ_BUILD_DATE = $(shell $(PYTHON) $(TOPSRCDIR)/platform/build/variables.py buildid_header | awk '{print $$3}')
  202. export MOZ_BUILD_DATE
  203. endif
  204. endif
  205. endif
  206. #####################################################
  207. # Preflight, before building any project
  208. realbuild preflight_all::
  209. ifeq (,$(MOZ_CURRENT_PROJECT)$(if $(MOZ_PREFLIGHT_ALL),,1))
  210. # Don't run preflight_all for individual projects in multi-project builds
  211. # (when MOZ_CURRENT_PROJECT is set.)
  212. ifndef MOZ_BUILD_PROJECTS
  213. # Building a single project, OBJDIR is usable.
  214. set -e; \
  215. for mkfile in $(MOZ_PREFLIGHT_ALL); do \
  216. $(MAKE) -f $(TOPSRCDIR)/$$mkfile preflight_all TOPSRCDIR=$(TOPSRCDIR) OBJDIR=$(OBJDIR) MOZ_OBJDIR=$(MOZ_OBJDIR); \
  217. done
  218. else
  219. # OBJDIR refers to the project-specific OBJDIR, which is not available at
  220. # this point when building multiple projects. Only MOZ_OBJDIR is available.
  221. set -e; \
  222. for mkfile in $(MOZ_PREFLIGHT_ALL); do \
  223. $(MAKE) -f $(TOPSRCDIR)/$$mkfile preflight_all TOPSRCDIR=$(TOPSRCDIR) MOZ_OBJDIR=$(MOZ_OBJDIR) MOZ_BUILD_PROJECTS='$(MOZ_BUILD_PROJECTS)'; \
  224. done
  225. endif
  226. endif
  227. # If we're building multiple projects, but haven't specified which project,
  228. # loop through them.
  229. ifeq (,$(MOZ_CURRENT_PROJECT)$(if $(MOZ_BUILD_PROJECTS),,1))
  230. configure realbuild preflight postflight $(OBJDIR_TARGETS)::
  231. set -e; \
  232. for app in $(MOZ_BUILD_PROJECTS); do \
  233. $(MAKE) -f $(TOPSRCDIR)/client.mk $@ MOZ_CURRENT_PROJECT=$$app; \
  234. done
  235. else
  236. # MOZ_CURRENT_PROJECT: either doing a single-project build, or building an
  237. # individual project in a multi-project build.
  238. ####################################
  239. # Configure
  240. MAKEFILE = $(wildcard $(OBJDIR)/Makefile)
  241. CONFIG_STATUS = $(wildcard $(OBJDIR)/config.status)
  242. CONFIG_CACHE = $(wildcard $(OBJDIR)/config.cache)
  243. EXTRA_CONFIG_DEPS := \
  244. $(TOPSRCDIR)/aclocal.m4 \
  245. $(TOPSRCDIR)/platform/aclocal.m4 \
  246. $(TOPSRCDIR)/platform/old-configure.in \
  247. $(wildcard $(TOPSRCDIR)/platform/build/autoconf/*.m4) \
  248. $(TOPSRCDIR)/platform/js/src/aclocal.m4 \
  249. $(TOPSRCDIR)/platform/js/src/old-configure.in \
  250. $(NULL)
  251. $(CONFIGURES): %: %.in $(EXTRA_CONFIG_DEPS)
  252. @echo Generating $@
  253. sed '1,/^divert/d' $< > $@
  254. chmod +x $@
  255. CONFIG_STATUS_DEPS := \
  256. $(wildcard $(TOPSRCDIR)/platform/ldap/sdks/c-sdk/configure) \
  257. $(wildcard $(TOPSRCDIR)/*/confvars.sh) \
  258. $(CONFIGURES) \
  259. $(TOPSRCDIR)/platform/CLOBBER \
  260. $(TOPSRCDIR)/platform/nsprpub/configure \
  261. $(TOPSRCDIR)/platform/config/milestone.txt \
  262. $(TOPSRCDIR)/platform/build/virtualenv_packages.txt \
  263. $(TOPSRCDIR)/platform/python/mozbuild/mozbuild/virtualenv.py \
  264. $(TOPSRCDIR)/platform/testing/mozbase/packages.txt \
  265. $(OBJDIR)/.mozconfig.json \
  266. $(NULL)
  267. CONFIGURE_ENV_ARGS += \
  268. MAKE='$(MAKE)' \
  269. $(NULL)
  270. # configure uses the program name to determine @srcdir@. Calling it without
  271. # $(TOPSRCDIR) will set @srcdir@ to "."; otherwise, it is set to the full
  272. # path of $(TOPSRCDIR).
  273. ifeq ($(TOPSRCDIR),$(OBJDIR))
  274. CONFIGURE = ./configure
  275. else
  276. CONFIGURE = $(TOPSRCDIR)/configure
  277. endif
  278. $(OBJDIR)/CLOBBER: $(TOPSRCDIR)/platform/CLOBBER
  279. $(PYTHON) $(TOPSRCDIR)/platform/config/pythonpath.py -I $(TOPSRCDIR)/platform/testing/mozbase/mozfile \
  280. $(TOPSRCDIR)/platform/python/mozbuild/mozbuild/controller/clobber.py $(TOPSRCDIR)/platform $(OBJDIR)
  281. configure-files: $(CONFIGURES)
  282. configure-preqs = \
  283. $(OBJDIR)/CLOBBER \
  284. configure-files \
  285. $(call mkdir_deps,$(OBJDIR)) \
  286. $(if $(MOZ_BUILD_PROJECTS),$(call mkdir_deps,$(MOZ_OBJDIR))) \
  287. save-mozconfig \
  288. $(OBJDIR)/.mozconfig.json \
  289. $(NULL)
  290. CREATE_MOZCONFIG_JSON = $(shell $(TOPSRCDIR)/mach environment --format=json -o $(OBJDIR)/.mozconfig.json)
  291. # Force CREATE_MOZCONFIG_JSON above to be resolved, without side effects in
  292. # case the result is non empty, and allowing an override on the make command
  293. # line not running the command (using := $(shell) still runs the shell command).
  294. ifneq (,$(CREATE_MOZCONFIG_JSON))
  295. endif
  296. $(OBJDIR)/.mozconfig.json: $(call mkdir_deps,$(OBJDIR)) ;
  297. save-mozconfig: $(FOUND_MOZCONFIG)
  298. ifdef FOUND_MOZCONFIG
  299. -cp $(FOUND_MOZCONFIG) $(OBJDIR)/.mozconfig
  300. endif
  301. configure:: $(configure-preqs)
  302. $(call BUILDSTATUS,TIERS configure)
  303. $(call BUILDSTATUS,TIER_START configure)
  304. @echo cd $(OBJDIR);
  305. @echo $(CONFIGURE) $(CONFIGURE_ARGS)
  306. @cd $(OBJDIR) && $(BUILD_PROJECT_ARG) $(CONFIGURE_ENV_ARGS) $(CONFIGURE) $(CONFIGURE_ARGS) \
  307. || ( echo '*** Fix above errors and then restart with\
  308. "$(MAKE) -f client.mk build"' && exit 1 )
  309. @touch $(OBJDIR)/Makefile
  310. $(call BUILDSTATUS,TIER_FINISH configure)
  311. ifneq (,$(MAKEFILE))
  312. $(OBJDIR)/Makefile: $(OBJDIR)/config.status
  313. $(OBJDIR)/config.status: $(CONFIG_STATUS_DEPS)
  314. else
  315. $(OBJDIR)/Makefile: $(CONFIG_STATUS_DEPS)
  316. endif
  317. @$(MAKE) -f $(TOPSRCDIR)/client.mk configure CREATE_MOZCONFIG_JSON=
  318. ifneq (,$(CONFIG_STATUS))
  319. $(OBJDIR)/config/autoconf.mk: $(TOPSRCDIR)/config/autoconf.mk.in
  320. $(PYTHON) $(OBJDIR)/config.status -n --file=$(OBJDIR)/config/autoconf.mk
  321. endif
  322. ####################################
  323. # Preflight
  324. realbuild preflight::
  325. ifdef MOZ_PREFLIGHT
  326. set -e; \
  327. for mkfile in $(MOZ_PREFLIGHT); do \
  328. $(MAKE) -f $(TOPSRCDIR)/$$mkfile preflight TOPSRCDIR=$(TOPSRCDIR) OBJDIR=$(OBJDIR) MOZ_OBJDIR=$(MOZ_OBJDIR); \
  329. done
  330. endif
  331. ####################################
  332. # Build it
  333. realbuild:: $(OBJDIR)/Makefile $(OBJDIR)/config.status
  334. +$(MOZ_MAKE)
  335. ####################################
  336. # Other targets
  337. # Pass these target onto the real build system
  338. $(OBJDIR_TARGETS):: $(OBJDIR)/Makefile $(OBJDIR)/config.status
  339. +$(MOZ_MAKE) $@
  340. ####################################
  341. # Postflight
  342. realbuild postflight::
  343. ifdef MOZ_POSTFLIGHT
  344. set -e; \
  345. for mkfile in $(MOZ_POSTFLIGHT); do \
  346. $(MAKE) -f $(TOPSRCDIR)/$$mkfile postflight TOPSRCDIR=$(TOPSRCDIR) OBJDIR=$(OBJDIR) MOZ_OBJDIR=$(MOZ_OBJDIR); \
  347. done
  348. endif
  349. endif # MOZ_CURRENT_PROJECT
  350. ####################################
  351. # Postflight, after building all projects
  352. ifdef MOZ_AUTOMATION
  353. ifndef MOZ_CURRENT_PROJECT
  354. $(if $(MOZ_PGO),profiledbuild,realbuild)::
  355. # Only run the automation/build target for the first project.
  356. # (i.e. first platform of universal builds)
  357. $(MAKE) -f $(TOPSRCDIR)/client.mk automation/build $(addprefix MOZ_CURRENT_PROJECT=,$(firstword $(MOZ_BUILD_PROJECTS)))
  358. endif
  359. endif
  360. realbuild postflight_all::
  361. ifeq (,$(MOZ_CURRENT_PROJECT)$(if $(MOZ_POSTFLIGHT_ALL),,1))
  362. # Don't run postflight_all for individual projects in multi-project builds
  363. # (when MOZ_CURRENT_PROJECT is set.)
  364. ifndef MOZ_BUILD_PROJECTS
  365. # Building a single project, OBJDIR is usable.
  366. set -e; \
  367. for mkfile in $(MOZ_POSTFLIGHT_ALL); do \
  368. $(MAKE) -f $(TOPSRCDIR)/$$mkfile postflight_all TOPSRCDIR=$(TOPSRCDIR) OBJDIR=$(OBJDIR) MOZ_OBJDIR=$(MOZ_OBJDIR); \
  369. done
  370. else
  371. # OBJDIR refers to the project-specific OBJDIR, which is not available at
  372. # this point when building multiple projects. Only MOZ_OBJDIR is available.
  373. set -e; \
  374. for mkfile in $(MOZ_POSTFLIGHT_ALL); do \
  375. $(MAKE) -f $(TOPSRCDIR)/$$mkfile postflight_all TOPSRCDIR=$(TOPSRCDIR) MOZ_OBJDIR=$(MOZ_OBJDIR) MOZ_BUILD_PROJECTS='$(MOZ_BUILD_PROJECTS)'; \
  376. done
  377. endif
  378. endif
  379. echo-variable-%:
  380. @echo $($*)
  381. # This makefile doesn't support parallel execution. It does pass
  382. # MOZ_MAKE_FLAGS to sub-make processes, so they will correctly execute
  383. # in parallel.
  384. .NOTPARALLEL:
  385. .PHONY: checkout \
  386. real_checkout \
  387. realbuild \
  388. build \
  389. profiledbuild \
  390. pull_all \
  391. build_all \
  392. clobber \
  393. clobber_all \
  394. pull_and_build_all \
  395. everything \
  396. configure \
  397. preflight_all \
  398. preflight \
  399. postflight \
  400. postflight_all \
  401. $(OBJDIR_TARGETS)