From dbad84b13105583e37ee536cd61bdf710567d0d8 Mon Sep 17 00:00:00 2001 From: Mike Hommey Date: Fri, 25 Jul 2014 07:14:40 +0900 Subject: [PATCH] Bug 1043344 - Move libraries and programs build to the compile tier. r=gps --- Makefile.in | 16 ++- config/Makefile.in | 6 +- config/config.mk | 7 -- config/makefiles/target_binaries.mk | 12 +-- config/nspr/Makefile.in | 5 +- config/recurse.mk | 37 ++++++- config/rules.mk | 15 ++- modules/libmar/tool/Makefile.in | 3 + moz.build | 17 ++- mozglue/build/Makefile.in | 2 +- .../mozbuild/backend/recursivemake.py | 100 ++++++++++++++---- python/mozbuild/mozbuild/frontend/emitter.py | 13 ++- python/mozbuild/mozbuild/frontend/reader.py | 9 +- .../mozbuild/frontend/sandbox_symbols.py | 20 ++-- security/build/Makefile.in | 4 +- toolkit/library/Makefile.in | 3 + toolkit/toolkit.mozbuild | 3 +- 17 files changed, 201 insertions(+), 71 deletions(-) diff --git a/Makefile.in b/Makefile.in index d1469ddb629..19429320a5b 100644 --- a/Makefile.in +++ b/Makefile.in @@ -317,5 +317,19 @@ endif js/xpconnect/src/export: dom/bindings/export xpcom/xpidl/export accessible/xpcom/export: xpcom/xpidl/export ifdef ENABLE_CLANG_PLUGIN -js/src/export config/export: build/clang-plugin/export +js/src/export config/host: build/clang-plugin/export +endif + +# Interdependencies that moz.build world don't know about yet for compilation. +# Note some others are hardcoded or "guessed" in recursivemake.py and emitter.py +ifeq ($(MOZ_WIDGET_TOOLKIT),gtk3) +toolkit/library/target: widget/gtk/mozgtk/gtk3/target +endif +ifndef MOZ_FOLD_LIBS +ifndef MOZ_NATIVE_SQLITE +security/build/target: db/sqlite3/src/target +endif +endif +ifeq ($(MOZ_REPLACE_MALLOC_LINKAGE),dummy library) +mozglue/build/target: memory/replace/dummy/target endif diff --git a/config/Makefile.in b/config/Makefile.in index 14bfc0d5cf7..c593a7d586e 100644 --- a/config/Makefile.in +++ b/config/Makefile.in @@ -4,10 +4,6 @@ # 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/. -# STDCXX_COMPAT is not needed here, and will actually fail because -# libstdc++-compat is not built yet. -MOZ_LIBSTDCXX_HOST_VERSION = - # IMPORTANT: Disable NSBUILDROOT for this directory only, otherwise we have # a recursive rule for finding nsinstall and the Perl scripts. ifdef NSBUILDROOT @@ -29,7 +25,7 @@ nsinstall$(HOST_BIN_SUFFIX): $(HOST_PROGRAM) NSINSTALL_EXECUTABLES := nsinstall$(HOST_BIN_SUFFIX) NSINSTALL_DEST := $(DIST)/bin -NSINSTALL_TARGET := export +NSINSTALL_TARGET := host INSTALL_TARGETS += NSINSTALL endif endif diff --git a/config/config.mk b/config/config.mk index 63d1f2229ab..2b3f0128b61 100644 --- a/config/config.mk +++ b/config/config.mk @@ -772,13 +772,6 @@ ifneq (,$(MOZ_LIBSTDCXX_TARGET_VERSION)$(MOZ_LIBSTDCXX_HOST_VERSION)) ifneq ($(OS_ARCH),Darwin) CHECK_STDCXX = @$(TOOLCHAIN_PREFIX)objdump -p $(1) | grep -e 'GLIBCXX_3\.4\.\(9\|[1-9][0-9]\)' > /dev/null && echo 'TEST-UNEXPECTED-FAIL | check_stdcxx | We do not want these libstdc++ symbols to be used:' && $(TOOLCHAIN_PREFIX)objdump -T $(1) | grep -e 'GLIBCXX_3\.4\.\(9\|[1-9][0-9]\)' && false || true endif - -ifdef MOZ_LIBSTDCXX_TARGET_VERSION -OS_LIBS += $(call EXPAND_LIBNAME_PATH,stdc++compat,$(DEPTH)/build/unix/stdc++compat) -endif -ifdef MOZ_LIBSTDCXX_HOST_VERSION -HOST_EXTRA_LIBS += $(call EXPAND_LIBNAME_PATH,host_stdc++compat,$(DEPTH)/build/unix/stdc++compat) -endif endif ifeq (,$(filter $(OS_TARGET),WINNT Darwin)) diff --git a/config/makefiles/target_binaries.mk b/config/makefiles/target_binaries.mk index 8fe0d1e7609..a837ec27bd7 100644 --- a/config/makefiles/target_binaries.mk +++ b/config/makefiles/target_binaries.mk @@ -23,7 +23,7 @@ ifndef NO_DIST_INSTALL ifneq (,$(strip $(PROGRAM)$(SIMPLE_PROGRAMS))) PROGRAMS_EXECUTABLES = $(SIMPLE_PROGRAMS) $(PROGRAM) PROGRAMS_DEST ?= $(FINAL_TARGET) -PROGRAMS_TARGET := binaries libs +PROGRAMS_TARGET := binaries libs target INSTALL_TARGETS += PROGRAMS endif @@ -34,7 +34,7 @@ $(error Shipping static component libs makes no sense.) else DIST_LIBRARY_FILES = $(LIBRARY) DIST_LIBRARY_DEST ?= $(DIST)/lib -DIST_LIBRARY_TARGET = binaries libs +DIST_LIBRARY_TARGET = binaries libs target INSTALL_TARGETS += DIST_LIBRARY endif endif # DIST_INSTALL @@ -45,7 +45,7 @@ ifdef SHARED_LIBRARY ifndef IS_COMPONENT SHARED_LIBRARY_FILES = $(SHARED_LIBRARY) SHARED_LIBRARY_DEST ?= $(FINAL_TARGET) -SHARED_LIBRARY_TARGET = binaries libs +SHARED_LIBRARY_TARGET = binaries libs target INSTALL_TARGETS += SHARED_LIBRARY ifneq (,$(filter WINNT,$(OS_ARCH))) @@ -57,7 +57,7 @@ IMPORT_LIB_FILES = $(SHARED_LIBRARY) endif IMPORT_LIB_DEST ?= $(DIST)/lib -IMPORT_LIB_TARGET = binaries libs +IMPORT_LIB_TARGET = binaries libs target ifdef IMPORT_LIB_FILES INSTALL_TARGETS += IMPORT_LIB endif @@ -68,14 +68,14 @@ endif # SHARED_LIBRARY ifneq (,$(strip $(HOST_SIMPLE_PROGRAMS)$(HOST_PROGRAM))) HOST_PROGRAMS_EXECUTABLES = $(HOST_SIMPLE_PROGRAMS) $(HOST_PROGRAM) HOST_PROGRAMS_DEST ?= $(DIST)/host/bin -HOST_PROGRAMS_TARGET = binaries libs +HOST_PROGRAMS_TARGET = binaries libs host INSTALL_TARGETS += HOST_PROGRAMS endif ifdef HOST_LIBRARY HOST_LIBRARY_FILES = $(HOST_LIBRARY) HOST_LIBRARY_DEST ?= $(DIST)/host/lib -HOST_LIBRARY_TARGET = binaries libs +HOST_LIBRARY_TARGET = binaries libs host INSTALL_TARGETS += HOST_LIBRARY endif diff --git a/config/nspr/Makefile.in b/config/nspr/Makefile.in index d284dafa04e..905f4b15dab 100644 --- a/config/nspr/Makefile.in +++ b/config/nspr/Makefile.in @@ -29,10 +29,11 @@ else export:: EXTRA_MAKE_FLAGS := SHARED_LIBRARY= IMPORT_LIBRARY= SHARED_LIB_PDB= endif -libs export clean distclean:: +clean distclean export:: $(MAKE) -C $(DEPTH)/nsprpub $@ $(EXTRA_MAKE_FLAGS) -libs:: +target:: + $(MAKE) -C $(DEPTH)/nsprpub libs $(EXTRA_MAKE_FLAGS) $(MAKE) -C $(DEPTH)/nsprpub install prefix=$(ABS_DIST)/sdk exec_prefix=$(ABS_DIST)/sdk bindir=$(ABS_DIST)/sdk/dummy includedir=$(ABS_DIST)/include/nspr libdir=$(ABS_DIST)/sdk/lib datadir=$(ABS_DIST)/sdk/dummy DESTDIR= $(EXTRA_MAKE_FLAGS) $(INSTALL) $(DEPTH)/nsprpub/config/nspr-config $(DIST)/sdk/bin $(RM) -rf $(DIST)/sdk/dummy diff --git a/config/recurse.mk b/config/recurse.mk index 5450593be45..499d0fbae48 100644 --- a/config/recurse.mk +++ b/config/recurse.mk @@ -76,10 +76,21 @@ WANT_STAMPS = 1 STAMP_TOUCH = $(TOUCH) $(@D)/binaries endif +# The compile tier has different rules from other tiers. +ifeq ($(CURRENT_TIER),compile) + +# Need a list of compile targets because we can't use pattern rules: +# https://savannah.gnu.org/bugs/index.php?42833 +.PHONY: $(compile_targets) +$(compile_targets): + $(call SUBMAKE,$(if $(filter $(@D),$(staticdirs)),,$(@F)),$(@D)) + +else + # Recursion rule for all directories traversed for all subtiers in the # current tier. $(addsuffix /$(CURRENT_TIER),$(CURRENT_DIRS)): %/$(CURRENT_TIER): - $(call SUBMAKE,$(if $(filter $*,$(staticdirs)),,$(CURRENT_TIER)),$*) + $(call SUBMAKE,$(CURRENT_TIER),$*) # Ensure existing stamps are up-to-date, but don't create one if submake didn't create one. $(if $(wildcard $@),@$(STAMP_TOUCH)) @@ -90,11 +101,27 @@ 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) +# At least build/export requires config/export for buildid, but who knows what +# else, so keep this global dependency to make config/export first for now. $(addsuffix /$(CURRENT_TIER),$(filter-out config,$(CURRENT_DIRS))): config/$(CURRENT_TIER) + +# The export tier requires nsinstall, which is built from config. So every +# subdirectory traversal needs to happen after building nsinstall in config, which +# is done with the config/host target. Note the config/host target only exists if +# nsinstall is actually built, which it is not on Windows, because we use +# nsinstall.py there. +ifeq ($(CURRENT_TIER),export) +ifneq (,$(filter config/host, $(compile_targets))) +$(addsuffix /$(CURRENT_TIER),$(CURRENT_DIRS)): config/host + +# Ensure rules for config/host and its possible dependencies. +.PHONY: $(filter %/host, $(compile_targets)) +$(filter %/host, $(compile_targets)): + $(call SUBMAKE,host,$(@D)) endif +endif + +endif # ifeq ($(CURRENT_TIER),compile) ifdef COMPILE_ENVIRONMENT # Disable dependency aggregation on PGO builds because of bug 934166. @@ -171,7 +198,7 @@ endif endef -$(foreach subtier,export compile binaries libs tools,$(eval $(call CREATE_SUBTIER_TRAVERSAL_RULE,$(subtier)))) +$(foreach subtier,export binaries libs tools,$(eval $(call CREATE_SUBTIER_TRAVERSAL_RULE,$(subtier)))) tools export:: $(SUBMAKEFILES) $(LOOP_OVER_TOOL_DIRS) diff --git a/config/rules.mk b/config/rules.mk index d61826f4992..73fc7366116 100644 --- a/config/rules.mk +++ b/config/rules.mk @@ -88,7 +88,7 @@ LIBS += $(NSPR_LIBS) ifndef MOZ_PROFILE_GENERATE CPP_UNIT_TESTS_FILES = $(CPP_UNIT_TESTS) CPP_UNIT_TESTS_DEST = $(DIST)/cppunittests -CPP_UNIT_TESTS_TARGET = libs +CPP_UNIT_TESTS_TARGET = binaries libs target INSTALL_TARGETS += CPP_UNIT_TESTS endif @@ -591,7 +591,11 @@ GLOBAL_DEPS += Makefile $(DEPTH)/config/autoconf.mk $(topsrcdir)/config/config.m ifdef COMPILE_ENVIRONMENT OBJ_TARGETS = $(OBJS) $(PROGOBJS) $(HOST_OBJS) $(HOST_PROGOBJS) -compile:: $(OBJ_TARGETS) +compile:: host target + +host:: $(HOST_LIBRARY) $(HOST_PROGRAM) $(HOST_SIMPLE_PROGRAMS) + +target:: $(LIBRARY) $(SHARED_LIBRARY) $(PROGRAM) $(SIMPLE_PROGRAMS) include $(topsrcdir)/config/makefiles/target_binaries.mk endif @@ -717,7 +721,7 @@ ifdef MOZ_PROFILE_GENERATE touch -t `date +%Y%m%d%H%M.%S -d 'now+5seconds'` pgo.relink endif else # !WINNT || GNU_CC - $(EXPAND_CCC) -o $@ $(CXXFLAGS) $(PROGOBJS) $(RESFILE) $(WIN32_EXE_LDFLAGS) $(LDFLAGS) $(WRAP_LDFLAGS) $(LIBS) $(MOZ_GLUE_PROGRAM_LDFLAGS) $(EXTRA_LIBS) $(OS_LIBS) $(BIN_FLAGS) $(EXE_DEF_FILE) $(STLPORT_LIBS) + $(EXPAND_CCC) -o $@ $(CXXFLAGS) $(PROGOBJS) $(RESFILE) $(WIN32_EXE_LDFLAGS) $(LDFLAGS) $(WRAP_LDFLAGS) $(MOZ_GLUE_PROGRAM_LDFLAGS) $(LIBS) $(EXTRA_LIBS) $(OS_LIBS) $(BIN_FLAGS) $(EXE_DEF_FILE) $(STLPORT_LIBS) $(call CHECK_BINARY,$@) endif # WINNT && !GNU_CC @@ -773,7 +777,7 @@ ifdef MSMANIFEST_TOOL fi endif # MSVC with manifest tool else - $(EXPAND_CCC) $(CXXFLAGS) -o $@ $< $(WIN32_EXE_LDFLAGS) $(LDFLAGS) $(WRAP_LDFLAGS) $(LIBS) $(MOZ_GLUE_PROGRAM_LDFLAGS) $(EXTRA_LIBS) $(OS_LIBS) $(BIN_FLAGS) $(STLPORT_LIBS) + $(EXPAND_CCC) $(CXXFLAGS) -o $@ $< $(WIN32_EXE_LDFLAGS) $(LDFLAGS) $(WRAP_LDFLAGS) $(MOZ_GLUE_PROGRAM_LDFLAGS) $(LIBS) $(EXTRA_LIBS) $(OS_LIBS) $(BIN_FLAGS) $(STLPORT_LIBS) $(call CHECK_BINARY,$@) endif # WINNT && !GNU_CC @@ -1269,6 +1273,7 @@ ifneq (,$(SDK_LIBRARY)) ifndef NO_DIST_INSTALL SDK_LIBRARY_FILES := $(SDK_LIBRARY) SDK_LIBRARY_DEST := $(SDK_LIB_DIR) +SDK_LIBRARY_TARGET := binaries libs target INSTALL_TARGETS += SDK_LIBRARY endif endif # SDK_LIBRARY @@ -1277,6 +1282,8 @@ ifneq (,$(strip $(SDK_BINARY))) ifndef NO_DIST_INSTALL SDK_BINARY_FILES := $(SDK_BINARY) SDK_BINARY_DEST := $(SDK_BIN_DIR) +# SDK_BINARY_TARGET is set in xpcom/idl-parser/Makefile.in +SDK_BINARY_TARGET ?= binaries libs target INSTALL_TARGETS += SDK_BINARY endif endif # SDK_BINARY diff --git a/modules/libmar/tool/Makefile.in b/modules/libmar/tool/Makefile.in index a2b89b45077..8a3f70ec484 100644 --- a/modules/libmar/tool/Makefile.in +++ b/modules/libmar/tool/Makefile.in @@ -18,6 +18,9 @@ HOST_CFLAGS += \ $(NULL) ifdef MOZ_ENABLE_SIGNMAR +# Please don't remove the following comment, because it does some magic: +# We don't want to use NSS_LIBS, presumably to avoid useless dependencies +# on parts of nss that don't matter. EXTRA_LIBS += \ $(DIST)/lib/$(LIB_PREFIX)nss3.$(LIB_SUFFIX) \ $(DIST)/lib/$(LIB_PREFIX)nssutil3.$(LIB_SUFFIX) \ diff --git a/moz.build b/moz.build index 51707189248..66dc1f2edc7 100644 --- a/moz.build +++ b/moz.build @@ -42,17 +42,24 @@ if not CONFIG['JS_STANDALONE']: if CONFIG['COMPILE_ENVIRONMENT'] and not CONFIG['LIBXUL_SDK']: if CONFIG['MOZ_BUILD_NSPR']: - add_tier_dir('nspr', 'config/nspr') + add_tier_dir('nspr', 'config/nspr', trigger='NSPR_LIBS') if not CONFIG['JS_STANDALONE']: add_tier_dir('external', 'config/external') if not CONFIG['MOZ_NATIVE_NSS']: - add_tier_dir('nss', 'security/build') + # We want security/build to be built before anything using + # NSPR_LIBS when MOZ_FOLD_LIBS is set, because that's where NSPR + # actually ends up being linked. All places using NSS_LIBS also + # use NSPR_LIBS so it's safe to use the latter. + add_tier_dir('nss', 'security/build', + trigger='NSPR_LIBS' if CONFIG['MOZ_FOLD_LIBS'] else 'NSS_LIBS') if CONFIG['BUILD_CTYPES'] and not CONFIG['MOZ_NATIVE_FFI']: - add_tier_dir('js', ['js/src/ctypes/libffi'], static=True) - add_tier_dir('js', ['intl/icu'], static=True) - CONFIGURE_SUBST_FILES += ['intl/icu/Makefile'] + add_tier_dir('js', ['js/src/ctypes/libffi'], static=True, + trigger='MOZ_FFI_LIBS') + if CONFIG['ENABLE_INTL_API'] and not CONFIG['MOZ_NATIVE_ICU']: + add_tier_dir('js', ['intl/icu'], static=True, trigger='MOZ_ICU_LIBS') + CONFIGURE_SUBST_FILES += ['intl/icu/Makefile'] add_tier_dir('js', ['js/src']) if not CONFIG['JS_STANDALONE']: diff --git a/mozglue/build/Makefile.in b/mozglue/build/Makefile.in index 3dfa7a44de9..6a9527f3102 100644 --- a/mozglue/build/Makefile.in +++ b/mozglue/build/Makefile.in @@ -126,7 +126,7 @@ ifeq (WINNT,$(OS_TARGET)) # ############################################################################### -libs:: mozcrt.lib +target:: mozcrt.lib $(INSTALL) $(IFLAGS2) mozcrt.lib $(DIST)/lib # And finally combine that with the jemalloc import library to get an import diff --git a/python/mozbuild/mozbuild/backend/recursivemake.py b/python/mozbuild/mozbuild/backend/recursivemake.py index f8f4a4ea8aa..d825b854acb 100644 --- a/python/mozbuild/mozbuild/backend/recursivemake.py +++ b/python/mozbuild/mozbuild/backend/recursivemake.py @@ -10,7 +10,10 @@ import logging import os import types -from collections import namedtuple +from collections import ( + defaultdict, + namedtuple, +) import mozwebidlcodegen from reftest import ReftestManifest @@ -319,6 +322,9 @@ class RecursiveMakeBackend(CommonBackend): ]} self._traversal = RecursiveMakeTraversal() + self._compile_graph = defaultdict(set) + self._triggers = defaultdict(set) + self._may_skip = { 'export': set(), 'compile': set(), @@ -505,18 +511,9 @@ class RecursiveMakeBackend(CommonBackend): if current in self._may_skip[tier] \ or current.startswith('subtiers/'): current = None - # subtiers/*_start and subtiers/*_finish, under subtiers/*, are - # kept sequential. Others are all forced parallel. - if current and current.startswith('subtiers/') and all_subdirs and \ - all_subdirs[0].startswith('subtiers/'): - return current, [], all_subdirs return current, all_subdirs, [] # build everything in parallel, including static dirs - def compile_filter(current, subdirs): - current, parallel, sequential = parallel_filter(current, subdirs) - return current, subdirs.static + parallel, sequential - # Skip tools dirs during libs traversal. Because of bug 925236 and # possible other unknown race conditions, don't parallelize the libs # tier. @@ -537,18 +534,17 @@ class RecursiveMakeBackend(CommonBackend): subdirs.dirs + subdirs.tests + subdirs.tools # compile, binaries and tools tiers use the same traversal as export - filters = { - 'export': parallel_filter, - 'compile': compile_filter, - 'binaries': parallel_filter, - 'libs': libs_filter, - 'tools': tools_filter, - } + filters = [ + ('export', parallel_filter), + ('binaries', parallel_filter), + ('libs', libs_filter), + ('tools', tools_filter), + ] root_deps_mk = Makefile() # Fill the dependencies for traversal of each tier. - for tier, filter in filters.items(): + for tier, filter in filters: main, all_deps = \ self._traversal.compute_dependencies(filter) for dir, deps in all_deps.items(): @@ -559,13 +555,29 @@ class RecursiveMakeBackend(CommonBackend): if main: rule.add_dependencies('%s/%s' % (d, tier) for d in main) + all_compile_deps = reduce(lambda x,y: x|y, + self._compile_graph.values()) if self._compile_graph else set() + compile_roots = set(self._compile_graph.keys()) - all_compile_deps + + rule = root_deps_mk.create_rule(['recurse_compile']) + rule.add_dependencies(compile_roots) + for target, deps in sorted(self._compile_graph.items()): + if deps: + rule = root_deps_mk.create_rule([target]) + rule.add_dependencies(deps) + root_mk = Makefile() # Fill root.mk with the convenience variables. - for tier, filter in filters.items(): + for tier, filter in filters: all_dirs = self._traversal.traverse('', filter) root_mk.add_statement('%s_dirs := %s' % (tier, ' '.join(all_dirs))) + # Need a list of compile targets because we can't use pattern rules: + # https://savannah.gnu.org/bugs/index.php?42833 + root_mk.add_statement('compile_targets := %s' % ' '.join(sorted( + set(self._compile_graph.keys()) | all_compile_deps))) + root_mk.add_statement('$(call include_deps,root-deps.mk)') with self._write_file( @@ -702,6 +714,14 @@ class RecursiveMakeBackend(CommonBackend): obj.topobjdir = bf.environment.topobjdir obj.config = bf.environment self._create_makefile(obj, stub=stub) + with open(obj.output_path) as fh: + content = fh.read() + for trigger, targets in self._triggers.items(): + if trigger.encode('ascii') in content: + for target in targets: + t = '%s/target' % mozpath.relpath(objdir, + bf.environment.topobjdir) + self._compile_graph[t].add(target) # Write out a master list of all IPDL source files. ipdl_dir = mozpath.join(self.environment.topobjdir, 'ipc', 'ipdl') @@ -809,6 +829,10 @@ class RecursiveMakeBackend(CommonBackend): self._traversal.add('', dirs=['subtiers/%s' % tier]) + for d in dirs + obj.tier_static_dirs[tier]: + if d.trigger: + self._triggers[d.trigger].add('%s/target' % d) + if obj.dirs: fh.write('DIRS := %s\n' % ' '.join(obj.dirs)) self._traversal.add(backend_file.relobjdir, dirs=relativize(obj.dirs)) @@ -847,8 +871,6 @@ class RecursiveMakeBackend(CommonBackend): # Until all SOURCES are really in moz.build, consider all directories # building binaries to require a pass at compile, too. if 'binaries' in affected_tiers: - affected_tiers.add('compile') - if 'compile' in affected_tiers or 'binaries' in affected_tiers: affected_tiers.add('libs') if obj.is_tool_dir and 'libs' in affected_tiers: affected_tiers.remove('libs') @@ -1020,6 +1042,11 @@ class RecursiveMakeBackend(CommonBackend): def _process_simple_program(self, obj, backend_file): if obj.is_unit_test: backend_file.write('CPP_UNIT_TESTS += %s\n' % obj.program) + # config.mk adds a dependency on NSPR_LIBS for CPP_UNIT_TESTS + # Add it here until moz.build land handles this. + if 'NSPR_LIBS' in self._triggers: + self._compile_graph[self._build_target_for_obj(obj)] |= \ + self._triggers['NSPR_LIBS'] else: backend_file.write('SIMPLE_PROGRAMS += %s\n' % obj.program) @@ -1144,6 +1171,10 @@ class RecursiveMakeBackend(CommonBackend): def _process_host_library(self, libdef, backend_file): backend_file.write('HOST_LIBRARY_NAME = %s\n' % libdef.basename) + @staticmethod + def _build_target_for_obj(obj): + return '%s/%s' % (obj.relobjdir, obj.KIND) + def _process_linked_libraries(self, obj, backend_file): def recurse_lib(lib): for l in lib.linked_libraries: @@ -1157,12 +1188,35 @@ class RecursiveMakeBackend(CommonBackend): # If this is an external objdir (i.e., comm-central), use the other # directory instead of $(DEPTH). if lib.objdir.startswith(topobjdir + '/'): - return '$(DEPTH)/%s' % mozpath.relpath(lib.objdir, topobjdir) + return '$(DEPTH)/%s' % lib.relobjdir else: - return mozpath.relpath(lib.objdir, obj.objdir) + return lib.relobjdir topobjdir = mozpath.normsep(obj.topobjdir) + # This will create the node even if there aren't any linked libraries. + build_target = self._build_target_for_obj(obj) + self._compile_graph[build_target] + + # Until MOZ_GLUE_LDFLAGS/MOZ_GLUE_PROGRAM_LDFLAGS are properly + # handled in moz.build world, assume any program or shared library + # we build depends on it. + if obj.KIND == 'target' and not isinstance(obj, StaticLibrary) and \ + build_target != 'mozglue/build/target' and \ + not obj.config.substs.get('JS_STANDALONE'): + self._compile_graph[build_target].add('mozglue/build/target') + if obj.config.substs.get('MOZ_MEMORY'): + self._compile_graph[build_target].add('memory/build/target') + + # Until STLPORT_LIBS are properly handled in moz.build world, assume + # any program or shared library we build depends on it. + if obj.KIND == 'target' and not isinstance(obj, StaticLibrary) and \ + build_target != 'build/stlport/target' and \ + 'stlport' in obj.config.substs.get('STLPORT_LIBS'): + self._compile_graph[build_target].add('build/stlport/target') + for lib in obj.linked_libraries: + self._compile_graph[build_target].add( + self._build_target_for_obj(lib)) relpath = pretty_relpath(lib) if isinstance(obj, Library): if isinstance(lib, StaticLibrary): diff --git a/python/mozbuild/mozbuild/frontend/emitter.py b/python/mozbuild/mozbuild/frontend/emitter.py index 0cafcf3e093..cf410c95627 100644 --- a/python/mozbuild/mozbuild/frontend/emitter.py +++ b/python/mozbuild/mozbuild/frontend/emitter.py @@ -226,7 +226,18 @@ class TreeMetadataEmitter(LoggingMixin): def _link_libraries(self, sandbox, obj, variable): """Add linkage declarations to a given object.""" assert isinstance(obj, Linkable) - for path in sandbox.get(variable, []): + + extra = [] + # Add stdc++compat library when wanted and needed + compat_varname = 'MOZ_LIBSTDCXX_%s_VERSION' % obj.KIND.upper() + if sandbox.config.substs.get(compat_varname) \ + and not isinstance(obj, (StaticLibrary, HostLibrary)): + extra.append({ + 'target': 'stdc++compat', + 'host': 'host_stdc++compat', + }[obj.KIND]) + + for path in sandbox.get(variable, []) + extra: force_static = path.startswith('static:') and obj.KIND == 'target' if force_static: path = path[7:] diff --git a/python/mozbuild/mozbuild/frontend/reader.py b/python/mozbuild/mozbuild/frontend/reader.py index 255bb0cf148..0ad7aeaa31b 100644 --- a/python/mozbuild/mozbuild/frontend/reader.py +++ b/python/mozbuild/mozbuild/frontend/reader.py @@ -103,6 +103,10 @@ def is_read_allowed(path, config): return False +class PathWithTrigger(unicode): + __slots__ = ('trigger',) + + class SandboxCalledError(SandboxError): """Represents an error resulting from calling the error() function.""" @@ -280,7 +284,8 @@ class MozbuildSandbox(Sandbox): data.is_library = True return data - def _add_tier_directory(self, tier, reldir, static=False, external=False): + def _add_tier_directory(self, tier, reldir, static=False, external=False, + trigger=None): """Register a tier directory with the build.""" if isinstance(reldir, text_type): reldir = [reldir] @@ -302,6 +307,8 @@ class MozbuildSandbox(Sandbox): raise Exception('Directory has already been registered with ' 'tier: %s' % path) + path = PathWithTrigger(path) + path.trigger = trigger self['TIERS'][tier][key].append(path) def _export(self, varname): diff --git a/python/mozbuild/mozbuild/frontend/sandbox_symbols.py b/python/mozbuild/mozbuild/frontend/sandbox_symbols.py index c9c68837172..94706dba174 100644 --- a/python/mozbuild/mozbuild/frontend/sandbox_symbols.py +++ b/python/mozbuild/mozbuild/frontend/sandbox_symbols.py @@ -50,10 +50,9 @@ class FinalTargetValue(SandboxDerivedValue, unicode): # Tier says for which specific tier the variable has an effect. # Valid tiers are: # - 'export' -# - 'compile': everything in relation with compiling objects. # - 'binaries': everything in relation with linking objects, producing # programs and libraries. -# - 'libs': everything that is not compile or binaries and that has +# - 'libs': everything that is not binaries and that has # traditionally been in the libs tier. # - 'tools' # A value of None means the variable has no direct effect on any tier. @@ -89,14 +88,14 @@ VARIABLES = { This variable contains a list of source code files to compile. Accepts assembler, C, C++, Objective C/C++. - """, 'compile'), + """, None), 'GENERATED_SOURCES': (StrictOrderingOnAppendList, list, """Generated source code files. This variable contains a list of generated source code files to compile. Accepts assembler, C, C++, Objective C/C++. - """, 'compile'), + """, None), 'FILES_PER_UNIFIED_FILE': (int, int, """The number of source files to compile into each unified source file. @@ -110,7 +109,7 @@ VARIABLES = { that can be concatenated all together and built as a single source file. This can help make the build faster and reduce the debug info size. - """, 'compile'), + """, None), 'GENERATED_UNIFIED_SOURCES': (StrictOrderingOnAppendList, list, """Generated source code files that can be compiled together. @@ -119,7 +118,7 @@ VARIABLES = { compile, that can be concatenated all together, with UNIFIED_SOURCES, and built as a single source file. This can help make the build faster and reduce the debug info size. - """, 'compile'), + """, None), 'GENERATED_FILES': (StrictOrderingOnAppendList, list, """Generic generated files. @@ -273,7 +272,7 @@ VARIABLES = { This variable contains a list of source code files to compile. with the host compiler. - """, 'compile'), + """, None), 'IS_COMPONENT': (bool, bool, """Whether the library contains a binary XPCOM component manifest. @@ -892,7 +891,7 @@ FUNCTIONS = { :py:class:`mozbuild.frontend.data.AndroidEclipseProjectData`. """), - 'add_tier_dir': ('_add_tier_directory', (str, [str, list], bool, bool), + 'add_tier_dir': ('_add_tier_directory', (str, [str, list], bool, bool, str), """Register a directory for tier traversal. This is the preferred way to populate the TIERS variable. @@ -929,6 +928,11 @@ FUNCTIONS = { content, but traversed with export, libs, and tools subtiers:: add_tier_dir('base', 'bar', external=True) + + Note there is a temporary ``trigger`` parameter that tells the build + system that if it sees the given string in a Makefile, then the compile + rules in that directory depend on the directories listed in the + add_tier_dir call. """), 'export': ('_export', (str,), diff --git a/security/build/Makefile.in b/security/build/Makefile.in index 8c3a32674ce..0aacacea096 100644 --- a/security/build/Makefile.in +++ b/security/build/Makefile.in @@ -303,6 +303,7 @@ endif # MOZ_FOLD_LIBS # Filter-out $(LIBRARY_NAME) because it's already handled in config/rules.mk. NSS_DIST_DLL_FILES := $(addprefix $(DIST)/lib/$(DLL_PREFIX),$(addsuffix $(DLL_SUFFIX),$(filter-out $(LIBRARY_NAME),$(NSS_DLLS)) $(NSS_EXTRA_DLLS))) NSS_DIST_DLL_DEST := $(DIST)/bin +NSS_DIST_DLL_TARGET := binaries libs target INSTALL_TARGETS += NSS_DIST_DLL ifeq ($(OS_ARCH)_$(1), SunOS_softokn3) @@ -315,6 +316,7 @@ NSS_SDK_LIB_FILES := \ $(addprefix $(DIST)/bin/$(DLL_PREFIX),$(addsuffix $(DLL_SUFFIX),$(NSS_DLLS))) \ $(NULL) NSS_SDK_LIB_DEST := $(DIST)/sdk/lib +NSS_SDK_LIB_TARGET := binaries libs target INSTALL_TARGETS += NSS_SDK_LIB ifdef MOZ_FOLD_LIBS @@ -453,7 +455,7 @@ $(addprefix clean-,$(NSS_DIRS)): clean-%: clean clobber clobber_all realclean distclean depend:: $(addprefix clean-,$(NSS_DIRS)) NSS_CMD_TARGETS := $(addprefix libs-,$(filter-out nss/cmd/lib,$(filter nss/cmd/%,$(NSS_DIRS)))) -libs:: $(NSS_CMD_TARGETS) +target:: $(NSS_CMD_TARGETS) ifdef MOZ_FOLD_LIBS $(NSS_CMD_TARGETS): $(addprefix $(DIST)/lib/$(IMPORT_PREFIX),$(addsuffix $(IMPORT_SUFFIX),$(NSS_LIBS))) diff --git a/toolkit/library/Makefile.in b/toolkit/library/Makefile.in index 60366e94c75..a91c3a391dc 100644 --- a/toolkit/library/Makefile.in +++ b/toolkit/library/Makefile.in @@ -7,6 +7,9 @@ CXXFLAGS += $(TK_CFLAGS) endif include $(topsrcdir)/toolkit/library/libxul.mk +# Please don't remove the following comment, because it does some magic: +# libxul.mk adds FT2_LIBS, NSS_LIBS and NSPR_LIBS, but we want to have the +# string in this file to trigger a dependency on freetype2, nss and nspr. ifeq (WINNT_1,$(OS_TARGET)_$(MOZ_PROFILE_USE)) # Wrap linker to measure peak virtual memory usage. diff --git a/toolkit/toolkit.mozbuild b/toolkit/toolkit.mozbuild index 345f841288e..20b9d686514 100644 --- a/toolkit/toolkit.mozbuild +++ b/toolkit/toolkit.mozbuild @@ -27,7 +27,8 @@ if CONFIG['MOZ_DMD']: add_tier_dir('platform', 'memory/replace/dmd') if CONFIG['MOZ_TREE_FREETYPE']: - add_tier_dir('platform', 'modules/freetype2', static=True) + add_tier_dir('platform', 'modules/freetype2', static=True, + trigger='FT2_LIBS') add_tier_dir('platform', 'xpcom')