Bug 738404 - Makefile.in edits to use threadsafe mkdir (bug 680246) - r=ted
authorJoey Armstrong <jarmstrong@mozilla.com>
Tue, 03 Apr 2012 16:08:16 -0400
changeset 94290 1f093ab9df776721fe2a3c9420c9bd5baf403e50
parent 94289 106c7696d3b7a4cf0bf25beb0225d80ed2f4c530
child 94291 c598b7b202e7c94f1135f4437898294548f53005
push idunknown
push userunknown
push dateunknown
reviewersted
bugs738404, 680246
milestone14.0a1
Bug 738404 - Makefile.in edits to use threadsafe mkdir (bug 680246) - r=ted
b2g/app/Makefile.in
build/win32/Makefile.in
client.mk
config/Makefile.in
config/config.mk
config/makefiles/autotargets.mk
config/makefiles/makeutils.mk
config/makefiles/test/Makefile.in
config/rules.mk
config/tests/makefiles/autodeps/Makefile.in
config/tests/makefiles/autodeps/testor.tmpl
dom/workers/test/extensions/bootstrap/Makefile.in
dom/workers/test/extensions/traditional/Makefile.in
js/src/config/Makefile.in
js/src/config/config.mk
js/src/config/makefiles/autotargets.mk
js/src/config/makefiles/makeutils.mk
js/src/config/rules.mk
--- a/b2g/app/Makefile.in
+++ b/b2g/app/Makefile.in
@@ -122,30 +122,34 @@ clean clobber repackage::
 	rm -rf $(DIST)/$(APP_NAME).app
 
 ifdef LIBXUL_SDK
 APPFILES = Resources
 else
 APPFILES = MacOS
 endif
 
-libs repackage::
-	mkdir -p $(DIST)/$(APP_NAME).app/Contents/MacOS
+libs-preqs = \
+  $(call mkdir_deps,$(DIST)/$(APP_NAME).app/Contents/MacOS) \
+  $(call mkdir_deps,$(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj) \
+  $(NULL)
+
+.PHONY: repackage
+libs repackage:: $(libs-preqs)
 	rsync -a --exclude "*.in" $(srcdir)/macbuild/Contents $(DIST)/$(APP_NAME).app --exclude English.lproj
-	mkdir -p $(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj
 	rsync -a --exclude "*.in" $(srcdir)/macbuild/Contents/Resources/English.lproj/ $(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj
 	sed -e "s/%MOZ_APP_VERSION%/$(MOZ_APP_VERSION)/" -e "s/%MOZ_APP_NAME%/$(MOZ_APP_NAME)/" -e "s/%APP_VERSION%/$(APP_VERSION)/" -e "s/%APP_NAME%/$(APP_NAME)/" -e "s/%APP_BINARY%/$(APP_BINARY)/" $(srcdir)/macbuild/Contents/Info.plist.in > $(DIST)/$(APP_NAME).app/Contents/Info.plist
 	sed -e "s/%APP_VERSION%/$(APP_VERSION)/" -e "s/%APP_NAME%/$(APP_NAME)/" $(srcdir)/macbuild/Contents/Resources/English.lproj/InfoPlist.strings.in | iconv -f UTF-8 -t UTF-16 > $(DIST)/$(APP_NAME).app/Contents/Resources/$(AB).lproj/InfoPlist.strings
 	rsync -a $(DIST)/bin/ $(DIST)/$(APP_NAME).app/Contents/$(APPFILES)
 	$(RM) $(DIST)/$(APP_NAME).app/Contents/$(APPFILES)/mangle $(DIST)/$(APP_NAME).app/Contents/$(APPFILES)/shlibsign
 ifdef LIBXUL_SDK
 	cp $(LIBXUL_DIST)/bin/xulrunner$(BIN_SUFFIX) $(DIST)/$(APP_NAME).app/Contents/MacOS/$(APP_BINARY)
 	rsync -a --exclude nsinstall --copy-unsafe-links $(LIBXUL_DIST)/XUL.framework $(DIST)/$(APP_NAME).app/Contents/Frameworks
 else
-	rm -f $(DIST)/$(APP_NAME).app/Contents/MacOS/$(PROGRAM)
+	$(RM) $(DIST)/$(APP_NAME).app/Contents/MacOS/$(PROGRAM)
 	rsync -aL $(PROGRAM) $(DIST)/$(APP_NAME).app/Contents/MacOS
 endif
 	printf "APPLMOZB" > $(DIST)/$(APP_NAME).app/Contents/PkgInfo
 
 else # MOZ_WIDGET_TOOLKIT != cocoa
 
 libs::
 ifdef LIBXUL_SDK
--- a/build/win32/Makefile.in
+++ b/build/win32/Makefile.in
@@ -30,20 +30,20 @@
 # use your version of this file under the terms of the MPL, indicate your
 # decision by deleting the provisions above and replace them with the notice
 # and other provisions required by the GPL or the LGPL. If you do not delete
 # the provisions above, a recipient may use your version of this file under
 # the terms of any one of the MPL, the GPL or the LGPL.
 #
 # ***** END LICENSE BLOCK *****
 
-DEPTH = ../..
+DEPTH     = ../..
 topsrcdir = @top_srcdir@
-srcdir = @srcdir@
-VPATH = @srcdir@
+srcdir    = @srcdir@
+VPATH     = @srcdir@
 
 include $(DEPTH)/config/autoconf.mk
 
 NO_PROFILE_GUIDED_OPTIMIZE = 1
 
 ifdef _MSC_VER
 ifneq ($(OS_TEST),x86_64)
 TEST_DIRS += vmwarerecordinghelper
@@ -97,18 +97,21 @@ endif
 ifeq (1700,$(_MSC_VER))
 REDIST_FILES = \
   msvcp110.dll \
   msvcr110.dll \
   $(NULL)
 endif
 
 ifdef REDIST_FILES
-libs::
-	mkdir -p $(FINAL_TARGET)
+libs-preqs = \
+  $(call mkdir_deps,$(FINAL_TARGET)) \
+  $(NULL)
+
+libs:: $(libs-preqs)
 	install --preserve-timestamps $(foreach f,$(REDIST_FILES),"$(WIN32_REDIST_DIR)"/$(f)) $(FINAL_TARGET)
 endif
 
 endif # ! MOZ_DEBUG
 endif # WIN32_REDIST_DIR
 
 # run the binscope tool to make sure the binary and all libraries
 # are using all available Windows OS-level security mechanisms
--- a/client.mk
+++ b/client.mk
@@ -96,17 +96,16 @@ endif
 # try to find autoconf 2.13 - discard errors from 'which'
 # MacOS X 10.4 sends "no autoconf*" errors to stdout, discard those via grep
 AUTOCONF ?= $(shell which autoconf-2.13 autoconf2.13 autoconf213 2>/dev/null | grep -v '^no autoconf' | head -1)
 
 ifeq (,$(strip $(AUTOCONF)))
 AUTOCONF=$(error Could not find autoconf 2.13)
 endif
 
-MKDIR := mkdir
 SH := /bin/sh
 PERL ?= perl
 PYTHON ?= python
 
 CONFIG_GUESS_SCRIPT := $(wildcard $(TOPSRCDIR)/build/autoconf/config.guess)
 ifdef CONFIG_GUESS_SCRIPT
   CONFIG_GUESS = $(shell $(CONFIG_GUESS_SCRIPT))
 endif
@@ -176,16 +175,19 @@ OBJDIR_TARGETS = install export libs cle
 
 #######################################################################
 # Rules
 
 # The default rule is build
 build::
 	$(MAKE) -f $(TOPSRCDIR)/client.mk $(if $(MOZ_PGO),profiledbuild,realbuild)
 
+# Define mkdir
+include $(TOPSRCDIR)/config/makefiles/makeutils.mk
+include $(TOPSRCDIR)/config/makefiles/autotargets.mk
 
 # Print out any options loaded from mozconfig.
 all realbuild clean depend distclean export libs install realclean::
 	@if test -f .mozconfig.out; then \
 	  cat .mozconfig.out; \
 	  rm -f .mozconfig.out; \
 	else true; \
 	fi
@@ -311,21 +313,23 @@ CONFIGURE_ENV_ARGS += \
 ifeq ($(TOPSRCDIR),$(OBJDIR))
   CONFIGURE = ./configure
 else
   CONFIGURE = $(TOPSRCDIR)/configure
 endif
 
 configure-files: $(CONFIGURES)
 
-configure:: configure-files
-ifdef MOZ_BUILD_PROJECTS
-	@if test ! -d $(MOZ_OBJDIR); then $(MKDIR) $(MOZ_OBJDIR); else true; fi
-endif
-	@if test ! -d $(OBJDIR); then $(MKDIR) $(OBJDIR); else true; fi
+configure-preqs = \
+  configure-files \
+  $(call mkdir_deps,$(OBJDIR)) \
+  $(if $(MOZ_BUILD_PROJECTS),$(call mkdir_deps,$(MOZ_OBJDIR))) \
+  $(NULL)
+
+configure:: $(configure-preqs)
 	@echo cd $(OBJDIR);
 	@echo $(CONFIGURE) $(CONFIGURE_ARGS)
 	@cd $(OBJDIR) && $(BUILD_PROJECT_ARG) $(CONFIGURE_ENV_ARGS) $(CONFIGURE) $(CONFIGURE_ARGS) \
 	  || ( echo "*** Fix above errors and then restart with\
                \"$(MAKE) -f client.mk build\"" && exit 1 )
 	@touch $(OBJDIR)/Makefile
 
 ifneq (,$(MAKEFILE))
--- a/config/Makefile.in
+++ b/config/Makefile.in
@@ -1,13 +1,47 @@
 # -*- Makefile -*-
 #
-# 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/.
+# ***** BEGIN LICENSE BLOCK *****
+# Version: MPL 1.1/GPL 2.0/LGPL 2.1
+#
+# The contents of this file are subject to the Mozilla Public License Version
+# 1.1 (the "License"); you may not use this file except in compliance with
+# the License. You may obtain a copy of the License at
+# http://www.mozilla.org/MPL/
+#
+# Software distributed under the License is distributed on an "AS IS" basis,
+# WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
+# for the specific language governing rights and limitations under the
+# License.
+#
+# The Original Code is mozilla.org code.
+#
+# The Initial Developer of the Original Code is
+# Netscape Communications Corporation.
+# Portions created by the Initial Developer are Copyright (C) 1998
+# the Initial Developer. All Rights Reserved.
+#
+# Contributor(s):
+#   Robert Ginda <rginda@netscape.com>
+#   John Taylor <jtaylor@netscape.com>
+#
+# Alternatively, the contents of this file may be used under the terms of
+# either of the GNU General Public License Version 2 or later (the "GPL"),
+# or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
+# in which case the provisions of the GPL or the LGPL are applicable instead
+# of those above. If you wish to allow use of your version of this file only
+# under the terms of either the GPL or the LGPL, and not to allow others to
+# use your version of this file under the terms of the MPL, indicate your
+# decision by deleting the provisions above and replace them with the notice
+# and other provisions required by the GPL or the LGPL. If you do not delete
+# the provisions above, a recipient may use your version of this file under
+# the terms of any one of the MPL, the GPL or the LGPL.
+#
+# ***** END LICENSE BLOCK *****
 
 DEPTH		= ..
 topsrcdir	= @top_srcdir@
 srcdir		= @srcdir@
 VPATH		= @srcdir@
 
 include $(DEPTH)/config/autoconf.mk
 
@@ -79,18 +113,21 @@ endif
 export::
 ifdef MOZ_BUILD_DATE
 	printf "%s" $(MOZ_BUILD_DATE) > buildid
 else
 	$(PYTHON) $(topsrcdir)/toolkit/xre/make-platformini.py --print-buildid > buildid
 endif
 
 ifdef WRAP_SYSTEM_INCLUDES
-export::
-	if test ! -d system_wrappers; then mkdir system_wrappers; fi
+export-preqs = \
+  $(call mkdir_deps,system_wrappers) \
+  $(NULL)
+
+export:: $(export-preqs)
 	$(PYTHON) $(topsrcdir)/config/Preprocessor.py $(DEFINES) $(ACDEFINES) \
 		-DMOZ_TREE_CAIRO=$(MOZ_TREE_CAIRO) \
 		-DMOZ_TREE_PIXMAN=$(MOZ_TREE_PIXMAN) \
 		-DMOZ_NATIVE_HUNSPELL=$(MOZ_NATIVE_HUNSPELL) \
 		-DMOZ_NATIVE_BZ2=$(MOZ_NATIVE_BZ2) \
 		-DMOZ_NATIVE_ZLIB=$(MOZ_NATIVE_ZLIB) \
 		-DMOZ_NATIVE_PNG=$(MOZ_NATIVE_PNG) \
 		-DMOZ_NATIVE_JPEG=$(MOZ_NATIVE_JPEG) \
@@ -152,21 +189,24 @@ PYUNITS := \
   unit-nsinstall.py \
   unit-printprereleasesuffix.py \
   unit-JarMaker.py \
   unit-buildlist.py \
   unit-expandlibs.py \
   unit-writemozinfo.py \
   $(NULL)
 
-check::\
-  check-python-modules check-jar-mn\
-  check-makefiles\
+check-preqs = \
+  check-python-modules \
+  check-jar-mn \
+  check-makefiles \
   $(NULL)
 
+check:: $(check-preqs)
+
 check-python-modules::
 	@$(EXIT_ON_ERROR) \
 	for test in $(PYUNITS); do \
 	  $(PYTHON) $(srcdir)/tests/$$test ; \
 	done
 
 check-jar-mn::
 	$(MAKE) -C tests/src-simple check-jar
--- a/config/config.mk
+++ b/config/config.mk
@@ -41,17 +41,17 @@
 #
 # Determines the platform and builds the macros needed to load the
 # appropriate platform-specific .mk file, then defines all (most?)
 # of the generic macros.
 #
 
 # Define an include-at-most-once flag
 ifdef INCLUDED_CONFIG_MK
-$(error Don't include config.mk twice!)
+$(error Do not include config.mk twice!)
 endif
 INCLUDED_CONFIG_MK = 1
 
 EXIT_ON_ERROR = set -e; # Shell loops continue past errors without this.
 
 ifndef topsrcdir
 topsrcdir	= $(DEPTH)
 endif
--- a/config/makefiles/autotargets.mk
+++ b/config/makefiles/autotargets.mk
@@ -6,32 +6,40 @@
 # You can obtain one at http://mozilla.org/MPL/2.0/.
 #
 
 ###########################################################################
 #      AUTO_DEPS - A list of deps/targets drived from other macros.
 #         *_DEPS - Make dependencies derived from a given macro.
 ###########################################################################
 
+MKDIR ?= mkdir -p
+TOUCH ?= touch
 
 ###########################################################################
 # Threadsafe directory creation
 # GENERATED_DIRS - Automated creation of these directories.
 ###########################################################################
-mkdir_deps =$(foreach dir,$($(1)),$(dir)/.mkdir.done)
+mkdir_deps =$(foreach dir,$(getargv),$(dir)/.mkdir.done)
 
 ifneq (,$(GENERATED_DIRS))
   tmpauto :=$(call mkdir_deps,GENERATED_DIRS)
   GENERATED_DIRS_DEPS +=$(tmpauto)
   GARBAGE_DIRS        +=$(tmpauto)
 endif
 
 %/.mkdir.done:
 	$(subst $(SPACE)-p,$(null),$(MKDIR)) -p $(dir $@)
 	@$(TOUCH) $@
 
 #################################################################
 # One ring/dep to rule them all:
 #   config/rules.mk::all target is available by default
 #   Add $(AUTO_DEPS) as an explicit target dependency when needed.
 #################################################################
+
 AUTO_DEPS +=$(GENERATED_DIRS_DEPS)
 
+
+# Complain loudly if deps have not loaded so getargv != $(NULL)
+ifndef getargv
+  $(error config/makefiles/makeutil.mk has not been included)
+endif
--- a/config/makefiles/makeutils.mk
+++ b/config/makefiles/makeutils.mk
@@ -29,22 +29,8 @@ argv +=)
 ###########################################################################
 ## Access function args as a simple list, inline within user functions.
 ## Usage: $(info ** $(call banner,$(getargv)))
 ##    $(call banner,scalar)
 ##    $(call banner,list0 list1 list2)
 ##    $(call banner,ref) ; ref=foo bar tans
 ## getarglist() would be a more accurate name but is longer to type
 getargv = $(if $(call isvar,$(1)),$($(1)),$(argv))
-
-## http://www.gnu.org/software/make/manual/make.html#Call-Function
-## Usage: o = $(call map,origin,o map $(MAKE))
-map = $(foreach val,$(2),$(call $(1),$(val)))
-
-
-# Usage: $(call checkIfEmpty,[error|warning] foo NULL bar)
-checkIfEmpty =$(foreach var,$(wordlist 2,100,$(getargv)),$(if $(strip $($(var))),$(NOP),$(call $(1),Variable $(var) does not contain a value)))
-
-# Usage: $(call errorIfEmpty,foo NULL bar)
-errorIfEmpty =$(call checkIfEmpty,error $(getargv))
-warnIfEmpty  =$(call checkIfEmpty,warning $(getargv))
-
-
--- a/config/makefiles/test/Makefile.in
+++ b/config/makefiles/test/Makefile.in
@@ -31,24 +31,16 @@ check::
 
 ## Logic processed at compile time so be selective about when to test
 ifneq ($(NULL),$(findstring check,$(MAKECMDGOALS)))
 
 $(info ===========================================================================)
 $(info Running test: $(MAKECMDGOALS): pwd=$(CURDIR))
 $(info ===========================================================================)
 
-
-ifdef VERBOSE
-$(info )
-$(info ===========================================================================)
-$(info Running test: istype, getargv)
-$(info ===========================================================================)
-endif
-
 ## Silent errors are oh so much fun
 ifndef istype
   $(error makeutils.mk was not included)
 endif
 
 # arg_scalar = [scalar|literal]
 arg_list = foo bar
 arg_ref  = arg_list
@@ -93,37 +85,11 @@ ifneq (scalar,$(call getargv,scalar))
 endif
 ifneq ($(arg_list),$(call getargv,arg_list))
   $(error getargv(arg_list)=list, found [$(call getargv,arg_list)])
 endif
 ifneq (arg_list,$(call getargv,arg_ref))
   $(error getargv(arg_ref)=list, found [$(call getargv,arg_ref)])
 endif
 
-
-ifdef MANUAL_TEST
-  # For automated testing a callback is needed that can set an external status
-  # variable that can be tested.  Syntax is tricky to get correct functionality.
-  ifdef VERBOSE
-    $(info )
-    $(info ===========================================================================)
-    $(info Running test: checkIfEmpty)
-    $(info ===========================================================================)
-  endif
-
-  #status =
-  #setTRUE =status=true
-  #setFALSE =status=$(NULL)
-  #$(call checkIfEmpty,setFALSE NULL)
-  #$(if $(status),$(error checkIfEmpty(xyz) failed))
-  #$(call checkIfEmpty,setTRUE xyz)
-  #$(if $(status),$(error checkIfEmpty(xyz) failed))
-  xyz=abc
-  $(info STATUS: warnIfEmpty - two vars)
-  $(call warnIfEmpty,foo xyz bar)
-  $(info STATUS: errorIfEmpty - on first var)
-  $(call errorIfEmpty,foo xyz bar)
-  $(error TEST FAILED: processing should not reach this point)
-endif
-
 endif # check in MAKECMDGOALS
 
 
--- a/config/rules.mk
+++ b/config/rules.mk
@@ -17,16 +17,19 @@ endif
 ifndef INCLUDED_CONFIG_MK
 include $(topsrcdir)/config/config.mk
 endif
 
 ifndef INCLUDED_VERSION_MK
 include $(topsrcdir)/config/version.mk
 endif
 
+include $(topsrcdir)/config/makefiles/makeutils.mk
+include $(topsrcdir)/config/makefiles/autotargets.mk
+
 ifdef SDK_XPIDLSRCS
 XPIDLSRCS += $(SDK_XPIDLSRCS)
 endif
 ifdef SDK_HEADERS
 EXPORTS += $(SDK_HEADERS)
 endif
 
 REPORT_BUILD = @echo $(notdir $<)
@@ -472,18 +475,18 @@ endif
 ifndef HOST_PROGOBJS
 HOST_PROGOBJS		= $(HOST_OBJS)
 endif
 
 # MAKE_DIRS: List of directories to build while looping over directories.
 # A Makefile that needs $(MDDEPDIR) created but doesn't set any of these
 # variables we know to check can just set NEED_MDDEPDIR explicitly.
 ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS)$(NEED_MDDEPDIR))
-MAKE_DIRS		+= $(CURDIR)/$(MDDEPDIR)
-GARBAGE_DIRS		+= $(MDDEPDIR)
+MAKE_DIRS       += $(CURDIR)/$(MDDEPDIR)
+GARBAGE_DIRS    += $(CURDIR)/$(MDDEPDIR)
 endif
 
 #
 # Tags: emacs (etags), vi (ctags)
 # TAG_PROGRAM := ctags -L -
 #
 TAG_PROGRAM		= xargs etags -a
 
@@ -1421,42 +1424,41 @@ export:: FORCE
 	@echo "*** Error processing XPIDLSRCS:"
 	@echo "Please define MODULE or XPIDL_MODULE when defining XPIDLSRCS,"
 	@echo "so we have a module name to use when creating MODULE.xpt."
 	@echo; sleep 2; false
 endif
 
 # generate .h files from into $(XPIDL_GEN_DIR), then export to $(DIST)/include;
 # warn against overriding existing .h file.
-$(XPIDL_GEN_DIR)/.done:
-	$(MKDIR) -p $(XPIDL_GEN_DIR)
-	@$(TOUCH) $@
-
-# don't depend on $(XPIDL_GEN_DIR), because the modification date changes
-# with any addition to the directory, regenerating all .h files -> everything.
 
 XPIDL_DEPS = \
   $(topsrcdir)/xpcom/idl-parser/header.py \
   $(topsrcdir)/xpcom/idl-parser/typelib.py \
   $(topsrcdir)/xpcom/idl-parser/xpidl.py \
   $(NULL)
 
-$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
+xpidl-preqs = \
+  $(call mkdir_deps,$(XPIDL_GEN_DIR)) \
+  $(call mkdir_deps,$(MDDEPDIR)) \
+  $(NULL)
+
+$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(xpidl-preqs)
 	$(REPORT_BUILD)
 	$(PYTHON_PATH) \
 	  -I$(topsrcdir)/other-licenses/ply \
 	  -I$(topsrcdir)/xpcom/idl-parser \
 	  $(topsrcdir)/xpcom/idl-parser/header.py --cachedir=$(DEPTH)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
 	@if test -n "$(findstring $*.h, $(EXPORTS))"; \
 	  then echo "*** WARNING: file $*.h generated from $*.idl overrides $(srcdir)/$*.h"; else true; fi
 
 ifndef NO_GEN_XPT
 # generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
 # into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
-$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
+$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(xpidl-preqs)
 	$(REPORT_BUILD)
 	$(PYTHON_PATH) \
 	  -I$(topsrcdir)/other-licenses/ply \
 	  -I$(topsrcdir)/xpcom/idl-parser \
 	  -I$(topsrcdir)/xpcom/typelib/xpt/tools \
 	  $(topsrcdir)/xpcom/idl-parser/typelib.py --cachedir=$(DEPTH)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
 
 # no need to link together if XPIDLSRCS contains only XPIDL_MODULE
@@ -1988,17 +1990,17 @@ FREEZE_VARIABLES = \
   EXTRA_PP_COMPONENTS \
   $(NULL)
 
 $(foreach var,$(FREEZE_VARIABLES),$(eval $(var)_FROZEN := '$($(var))'))
 
 CHECK_FROZEN_VARIABLES = $(foreach var,$(FREEZE_VARIABLES), \
   $(if $(subst $($(var)_FROZEN),,'$($(var))'),$(error Makefile variable '$(var)' changed value after including rules.mk. Was $($(var)_FROZEN), now $($(var)).)))
 
-libs export libs::
+libs export::
 	$(CHECK_FROZEN_VARIABLES)
 
 default all::
 	if test -d $(DIST)/bin ; then touch $(DIST)/bin/.purgecaches ; fi
 
 
 #############################################################################
 # Derived targets and dependencies
--- a/config/tests/makefiles/autodeps/Makefile.in
+++ b/config/tests/makefiles/autodeps/Makefile.in
@@ -12,17 +12,16 @@ PYTEST = $(PYTHON) -E
 export PYTHONDONTWRITEBYTECODE=1
 
 DEPTH     = ../../../..
 topsrcdir = @top_srcdir@
 srcdir    = @srcdir@
 VPATH     = @srcdir@
 
 include $(DEPTH)/config/autoconf.mk
-# INCLUDED_CONFIG_MK = 1
 include $(topsrcdir)/config/config.mk
 include $(topsrcdir)/config/rules.mk
 
 autotgt_tests = .deps/autotargets.mk.ts
 
 tgts =\
   .deps/.mkdir.done\
   $(autotgt_tests)
@@ -33,12 +32,10 @@ tgts =\
 ##---]  TARGETS  [---##
 ##------------------_##
 all::
 
 check:: $(tgts)
 
 # Only run unit test when autotargets.mk is modified
 $(autotgt_tests): $(topsrcdir)/config/makefiles/autotargets.mk
-	echo "MAKECMD=$(MAKE)"
 	MAKECMD=$(MAKE) $(PYTEST) $(srcdir)/check_mkdir.tpy
 	@$(TOUCH) $@
-
--- a/config/tests/makefiles/autodeps/testor.tmpl
+++ b/config/tests/makefiles/autodeps/testor.tmpl
@@ -12,16 +12,17 @@
 deps =$(NULL)
 tgts =$(NULL)
 
 ifdef VERBOSE
   tgts += show
 endif
 
 # Define macros
+include $(topsrcdir)/config/makefiles/makeutils.mk
 include $(topsrcdir)/config/makefiles/autotargets.mk
 
 ##########################
 ## Verify threadsafe mkdir
 ##########################
 ifdef deps_mkdir_bycall
   deps += $(call mkdir_deps,deps_mkdir_bycall)
   tgts += check_mkdir
--- a/dom/workers/test/extensions/bootstrap/Makefile.in
+++ b/dom/workers/test/extensions/bootstrap/Makefile.in
@@ -47,13 +47,14 @@ XPI_NAME = workerbootstrap
 DIST_FILES = \
   bootstrap.js \
   install.rdf \
   worker.js \
   $(NULL)
 
 TEST_EXTENSIONS_DIR = $(DEPTH)/_tests/testing/mochitest/extensions
 
+GENERATED_DIRS = $(TEST_EXTENSIONS_DIR)
+
 include $(topsrcdir)/config/rules.mk
 
 libs::
-	$(MKDIR) -p $(TEST_EXTENSIONS_DIR)
 	@(cd $(DIST)/xpi-stage && tar $(TAR_CREATE_FLAGS) - $(XPI_NAME)) | (cd $(TEST_EXTENSIONS_DIR) && tar -xf -)
--- a/dom/workers/test/extensions/traditional/Makefile.in
+++ b/dom/workers/test/extensions/traditional/Makefile.in
@@ -56,13 +56,14 @@ EXTRA_COMPONENTS = \
 
 DIST_FILES = \
   install.rdf \
   worker.js \
   $(NULL)
 
 TEST_EXTENSIONS_DIR = $(DEPTH)/_tests/testing/mochitest/extensions
 
+GENERATED_DIRS = $(TEST_EXTENSIONS_DIR)
+
 include $(topsrcdir)/config/rules.mk
 
 libs::
-	$(MKDIR) -p $(TEST_EXTENSIONS_DIR)
 	@(cd $(DIST)/xpi-stage && tar $(TAR_CREATE_FLAGS) - $(XPI_NAME)) | (cd $(TEST_EXTENSIONS_DIR) && tar -xf -)
--- a/js/src/config/Makefile.in
+++ b/js/src/config/Makefile.in
@@ -84,18 +84,19 @@ include $(topsrcdir)/config/rules.mk
 HOST_CFLAGS += -DUNICODE -D_UNICODE
 
 export:: $(TARGETS)
 ifdef HOST_PROGRAM
 	$(INSTALL) $(HOST_PROGRAM) $(DIST)/bin
 endif
 
 ifdef WRAP_SYSTEM_INCLUDES
-export::
-	if test ! -d system_wrappers_js; then mkdir system_wrappers_js; fi
+export:: \
+  $(call mkdir_deps,system_wrappers_js) \
+  $(NULL)
 	$(PYTHON) $(srcdir)/Preprocessor.py $(DEFINES) $(ACDEFINES) \
 		$(srcdir)/system-headers | $(PERL) $(srcdir)/make-system-wrappers.pl system_wrappers_js
 	$(INSTALL) system_wrappers_js $(DIST)
 
 GARBAGE_DIRS += system_wrappers_js
 endif
 
 GARBAGE += $(srcdir)/*.pyc *.pyc
--- a/js/src/config/config.mk
+++ b/js/src/config/config.mk
@@ -41,17 +41,17 @@
 #
 # Determines the platform and builds the macros needed to load the
 # appropriate platform-specific .mk file, then defines all (most?)
 # of the generic macros.
 #
 
 # Define an include-at-most-once flag
 ifdef INCLUDED_CONFIG_MK
-$(error Don't include config.mk twice!)
+$(error Do not include config.mk twice!)
 endif
 INCLUDED_CONFIG_MK = 1
 
 EXIT_ON_ERROR = set -e; # Shell loops continue past errors without this.
 
 ifndef topsrcdir
 topsrcdir	= $(DEPTH)
 endif
--- a/js/src/config/makefiles/autotargets.mk
+++ b/js/src/config/makefiles/autotargets.mk
@@ -6,32 +6,40 @@
 # You can obtain one at http://mozilla.org/MPL/2.0/.
 #
 
 ###########################################################################
 #      AUTO_DEPS - A list of deps/targets drived from other macros.
 #         *_DEPS - Make dependencies derived from a given macro.
 ###########################################################################
 
+MKDIR ?= mkdir -p
+TOUCH ?= touch
 
 ###########################################################################
 # Threadsafe directory creation
 # GENERATED_DIRS - Automated creation of these directories.
 ###########################################################################
-mkdir_deps =$(foreach dir,$($(1)),$(dir)/.mkdir.done)
+mkdir_deps =$(foreach dir,$(getargv),$(dir)/.mkdir.done)
 
 ifneq (,$(GENERATED_DIRS))
   tmpauto :=$(call mkdir_deps,GENERATED_DIRS)
   GENERATED_DIRS_DEPS +=$(tmpauto)
   GARBAGE_DIRS        +=$(tmpauto)
 endif
 
 %/.mkdir.done:
 	$(subst $(SPACE)-p,$(null),$(MKDIR)) -p $(dir $@)
 	@$(TOUCH) $@
 
 #################################################################
 # One ring/dep to rule them all:
 #   config/rules.mk::all target is available by default
 #   Add $(AUTO_DEPS) as an explicit target dependency when needed.
 #################################################################
+
 AUTO_DEPS +=$(GENERATED_DIRS_DEPS)
 
+
+# Complain loudly if deps have not loaded so getargv != $(NULL)
+ifndef getargv
+  $(error config/makefiles/makeutil.mk has not been included)
+endif
--- a/js/src/config/makefiles/makeutils.mk
+++ b/js/src/config/makefiles/makeutils.mk
@@ -29,22 +29,8 @@ argv +=)
 ###########################################################################
 ## Access function args as a simple list, inline within user functions.
 ## Usage: $(info ** $(call banner,$(getargv)))
 ##    $(call banner,scalar)
 ##    $(call banner,list0 list1 list2)
 ##    $(call banner,ref) ; ref=foo bar tans
 ## getarglist() would be a more accurate name but is longer to type
 getargv = $(if $(call isvar,$(1)),$($(1)),$(argv))
-
-## http://www.gnu.org/software/make/manual/make.html#Call-Function
-## Usage: o = $(call map,origin,o map $(MAKE))
-map = $(foreach val,$(2),$(call $(1),$(val)))
-
-
-# Usage: $(call checkIfEmpty,[error|warning] foo NULL bar)
-checkIfEmpty =$(foreach var,$(wordlist 2,100,$(getargv)),$(if $(strip $($(var))),$(NOP),$(call $(1),Variable $(var) does not contain a value)))
-
-# Usage: $(call errorIfEmpty,foo NULL bar)
-errorIfEmpty =$(call checkIfEmpty,error $(getargv))
-warnIfEmpty  =$(call checkIfEmpty,warning $(getargv))
-
-
--- a/js/src/config/rules.mk
+++ b/js/src/config/rules.mk
@@ -17,16 +17,19 @@ endif
 ifndef INCLUDED_CONFIG_MK
 include $(topsrcdir)/config/config.mk
 endif
 
 ifndef INCLUDED_VERSION_MK
 include $(topsrcdir)/config/version.mk
 endif
 
+include $(topsrcdir)/config/makefiles/makeutils.mk
+include $(topsrcdir)/config/makefiles/autotargets.mk
+
 ifdef SDK_XPIDLSRCS
 XPIDLSRCS += $(SDK_XPIDLSRCS)
 endif
 ifdef SDK_HEADERS
 EXPORTS += $(SDK_HEADERS)
 endif
 
 REPORT_BUILD = @echo $(notdir $<)
@@ -472,18 +475,18 @@ endif
 ifndef HOST_PROGOBJS
 HOST_PROGOBJS		= $(HOST_OBJS)
 endif
 
 # MAKE_DIRS: List of directories to build while looping over directories.
 # A Makefile that needs $(MDDEPDIR) created but doesn't set any of these
 # variables we know to check can just set NEED_MDDEPDIR explicitly.
 ifneq (,$(OBJS)$(XPIDLSRCS)$(SIMPLE_PROGRAMS)$(NEED_MDDEPDIR))
-MAKE_DIRS		+= $(CURDIR)/$(MDDEPDIR)
-GARBAGE_DIRS		+= $(MDDEPDIR)
+MAKE_DIRS       += $(CURDIR)/$(MDDEPDIR)
+GARBAGE_DIRS    += $(CURDIR)/$(MDDEPDIR)
 endif
 
 #
 # Tags: emacs (etags), vi (ctags)
 # TAG_PROGRAM := ctags -L -
 #
 TAG_PROGRAM		= xargs etags -a
 
@@ -1421,42 +1424,41 @@ export:: FORCE
 	@echo "*** Error processing XPIDLSRCS:"
 	@echo "Please define MODULE or XPIDL_MODULE when defining XPIDLSRCS,"
 	@echo "so we have a module name to use when creating MODULE.xpt."
 	@echo; sleep 2; false
 endif
 
 # generate .h files from into $(XPIDL_GEN_DIR), then export to $(DIST)/include;
 # warn against overriding existing .h file.
-$(XPIDL_GEN_DIR)/.done:
-	$(MKDIR) -p $(XPIDL_GEN_DIR)
-	@$(TOUCH) $@
-
-# don't depend on $(XPIDL_GEN_DIR), because the modification date changes
-# with any addition to the directory, regenerating all .h files -> everything.
 
 XPIDL_DEPS = \
   $(topsrcdir)/xpcom/idl-parser/header.py \
   $(topsrcdir)/xpcom/idl-parser/typelib.py \
   $(topsrcdir)/xpcom/idl-parser/xpidl.py \
   $(NULL)
 
-$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
+xpidl-preqs = \
+  $(call mkdir_deps,$(XPIDL_GEN_DIR)) \
+  $(call mkdir_deps,$(MDDEPDIR)) \
+  $(NULL)
+
+$(XPIDL_GEN_DIR)/%.h: %.idl $(XPIDL_DEPS) $(xpidl-preqs)
 	$(REPORT_BUILD)
 	$(PYTHON_PATH) \
 	  -I$(topsrcdir)/other-licenses/ply \
 	  -I$(topsrcdir)/xpcom/idl-parser \
 	  $(topsrcdir)/xpcom/idl-parser/header.py --cachedir=$(DEPTH)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
 	@if test -n "$(findstring $*.h, $(EXPORTS))"; \
 	  then echo "*** WARNING: file $*.h generated from $*.idl overrides $(srcdir)/$*.h"; else true; fi
 
 ifndef NO_GEN_XPT
 # generate intermediate .xpt files into $(XPIDL_GEN_DIR), then link
 # into $(XPIDL_MODULE).xpt and export it to $(FINAL_TARGET)/components.
-$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(XPIDL_GEN_DIR)/.done
+$(XPIDL_GEN_DIR)/%.xpt: %.idl $(XPIDL_DEPS) $(xpidl-preqs)
 	$(REPORT_BUILD)
 	$(PYTHON_PATH) \
 	  -I$(topsrcdir)/other-licenses/ply \
 	  -I$(topsrcdir)/xpcom/idl-parser \
 	  -I$(topsrcdir)/xpcom/typelib/xpt/tools \
 	  $(topsrcdir)/xpcom/idl-parser/typelib.py --cachedir=$(DEPTH)/xpcom/idl-parser $(XPIDL_FLAGS) $(_VPATH_SRCS) -d $(MDDEPDIR)/$(@F).pp -o $@
 
 # no need to link together if XPIDLSRCS contains only XPIDL_MODULE
@@ -1988,17 +1990,17 @@ FREEZE_VARIABLES = \
   EXTRA_PP_COMPONENTS \
   $(NULL)
 
 $(foreach var,$(FREEZE_VARIABLES),$(eval $(var)_FROZEN := '$($(var))'))
 
 CHECK_FROZEN_VARIABLES = $(foreach var,$(FREEZE_VARIABLES), \
   $(if $(subst $($(var)_FROZEN),,'$($(var))'),$(error Makefile variable '$(var)' changed value after including rules.mk. Was $($(var)_FROZEN), now $($(var)).)))
 
-libs export libs::
+libs export::
 	$(CHECK_FROZEN_VARIABLES)
 
 default all::
 	if test -d $(DIST)/bin ; then touch $(DIST)/bin/.purgecaches ; fi
 
 
 #############################################################################
 # Derived targets and dependencies