Merge "Tighten restrictions on LOCAL_JACK_COVERAGE_(INCLUDE|EXCLUDE)_FILTER"
diff --git a/core/Makefile b/core/Makefile
index 4ef0d89..a9bd1c2 100644
--- a/core/Makefile
+++ b/core/Makefile
@@ -517,6 +517,20 @@
 $(call dist-for-goals,droidcore,$(SOONG_TO_CONVERT))
 
 # -----------------------------------------------------------------
+# Modules use -Wno-error, or added default -Wall -Werror
+WALL_WERROR := $(PRODUCT_OUT)/wall_werror.txt
+$(WALL_WERROR):
+	@rm -f $@
+	echo "# Modules using -Wno-error" >> $@
+	for m in $(sort $(SOONG_MODULES_USING_WNO_ERROR) $(MODULES_USING_WNO_ERROR)); do echo $$m >> $@; done
+	echo "# Modules added default -Wall -Werror" >> $@
+	for m in $(sort $(SOONG_MODULES_ADDED_WERROR) $(MODULES_ADDED_WERROR)); do echo $$m >> $@; done
+	echo "# Modules added default -Wall" >> $@
+	for m in $(sort $(SOONG_MODULES_ADDED_WALL) $(MODULES_ADDED_WALL)); do echo $$m >> $@; done
+
+$(call dist-for-goals,droidcore,$(WALL_WERROR))
+
+# -----------------------------------------------------------------
 # The dev key is used to sign this package, and as the key required
 # for future OTA packages installed by this system.  Actual product
 # deliverables will be re-signed by hand.  We expect this file to
@@ -1176,14 +1190,6 @@
 RECOVERY_RESOURCE_ZIP :=
 endif
 
-ifeq ($(TARGET_PRIVATE_RES_DIRS),)
-  $(info No private recovery resources for TARGET_DEVICE $(TARGET_DEVICE))
-endif
-
-ifeq ($(recovery_fstab),)
-  $(info No recovery.fstab for TARGET_DEVICE $(TARGET_DEVICE))
-endif
-
 INTERNAL_RECOVERYIMAGE_ARGS := \
 	$(addprefix --second ,$(INSTALLED_2NDBOOTLOADER_TARGET)) \
 	--kernel $(recovery_kernel) \
@@ -2179,7 +2185,7 @@
   $(shell find system/update_engine/scripts -name \*.pyc -prune -o -type f -print | sort) \
   $(shell find build/target/product/security -type f -name \*.x509.pem -o -name \*.pk8 -o \
       -name verity_key | sort) \
-  $(shell find device vendor -type f -name \*.pk8 -o -name verifiedboot\* -o \
+  $(shell find device $(wildcard vendor) -type f -name \*.pk8 -o -name verifiedboot\* -o \
       -name \*.x509.pem -o -name oem\*.prop | sort)
 
 OTATOOLS_RELEASETOOLS := \
diff --git a/core/base_rules.mk b/core/base_rules.mk
index b501fbd..592650d 100644
--- a/core/base_rules.mk
+++ b/core/base_rules.mk
@@ -65,6 +65,16 @@
   my_host_cross :=
 endif
 
+_path := $(LOCAL_MODULE_PATH) $(LOCAL_MODULE_PATH_32) $(LOCAL_MODULE_PATH_64)
+ifneq ($(filter $(TARGET_OUT_VENDOR)%,$(_path)),)
+LOCAL_VENDOR_MODULE := true
+else ifneq ($(filter $(TARGET_OUT_OEM)/%,$(_path)),)
+LOCAL_OEM_MODULE := true
+else ifneq ($(filter $(TARGET_OUT_ODM)/%,$(_path)),)
+LOCAL_ODM_MODULE := true
+endif
+_path :=
+
 ifndef LOCAL_PROPRIETARY_MODULE
   LOCAL_PROPRIETARY_MODULE := $(LOCAL_VENDOR_MODULE)
 endif
diff --git a/core/binary.mk b/core/binary.mk
index bd1e601..e54edbe 100644
--- a/core/binary.mk
+++ b/core/binary.mk
@@ -1330,6 +1330,22 @@
 asm_objects += $(asm_objects_asm)
 endif
 
+###################################################################
+## When compiling a CFI enabled target, use the .cfi variant of any
+## static dependencies (where they exist).
+##################################################################
+define use_soong_cfi_static_libraries
+  $(foreach l,$(1),$(if $(filter $(l),$(SOONG_CFI_STATIC_LIBRARIES)),\
+      $(l).cfi,$(l)))
+endef
+
+ifneq ($(filter cfi,$(my_sanitize)),)
+  my_whole_static_libraries := $(call use_soong_cfi_static_libraries,\
+    $(my_whole_static_libraries))
+  my_static_libraries := $(call use_soong_cfi_static_libraries,\
+    $(my_static_libraries))
+endif
+
 ###########################################################
 ## When compiling against the VNDK, use LL-NDK libraries
 ###########################################################
@@ -1664,13 +1680,31 @@
     my_cflags += -DANDROID_STRICT
 endif
 
-# Add -Werror if LOCAL_PATH is in the WARNING_DISALLOWED project list,
-# or not in the WARNING_ALLOWED project list.
-ifneq (,$(strip $(call find_warning_disallowed_projects,$(LOCAL_PATH))))
-  my_cflags_no_override += -Werror
-else
-  ifeq (,$(strip $(call find_warning_allowed_projects,$(LOCAL_PATH))))
-    my_cflags_no_override += -Werror
+# Check if -Werror or -Wno-error is used in C compiler flags.
+# Modules defined in $(SOONG_ANDROID_MK) are checked in soong's cc.go.
+ifneq ($(LOCAL_MODULE_MAKEFILE),$(SOONG_ANDROID_MK))
+  # Header libraries do not need cflags.
+  ifneq (HEADER_LIBRARIES,$(LOCAL_MODULE_CLASS))
+    # Prebuilt modules do not need cflags.
+    ifeq (,$(LOCAL_PREBUILT_MODULE_FILE))
+      my_all_cflags := $(my_cflags) $(my_cppflags) $(my_cflags_no_override)
+      # Issue warning if -Wno-error is used.
+      ifneq (,$(filter -Wno-error,$(my_all_cflags)))
+        $(eval MODULES_USING_WNO_ERROR := $(MODULES_USING_WNO_ERROR) $(LOCAL_MODULE_MAKEFILE):$(LOCAL_MODULE))
+      else
+        # Issue warning if -Werror is not used. Add it.
+        ifeq (,$(filter -Werror,$(my_all_cflags)))
+          # Add -Wall -Werror unless the project is in the WARNING_ALLOWED project list.
+          ifeq (,$(strip $(call find_warning_allowed_projects,$(LOCAL_PATH))))
+            $(eval MODULES_ADDED_WERROR := $(MODULES_ADDED_WERROR) $(LOCAL_MODULE_MAKEFILE):$(LOCAL_MODULE))
+            my_cflags := -Wall -Werror $(my_cflags)
+          else
+            $(eval MODULES_ADDED_WALL := $(MODULES_ADDED_WALL) $(LOCAL_MODULE_MAKEFILE):$(LOCAL_MODULE))
+            my_cflags := -Wall $(my_cflags)
+          endif
+        endif
+      endif
+    endif
   endif
 endif
 
diff --git a/core/config.mk b/core/config.mk
index bebc186..1994899 100644
--- a/core/config.mk
+++ b/core/config.mk
@@ -898,38 +898,7 @@
 APPS_DEFAULT_VERSION_NAME := $(PLATFORM_VERSION)
 endif
 
-# Projects clean of compiler warnings should be compiled with -Werror.
-# If most modules in a directory such as external/ have warnings,
-# the directory should be in ANDROID_WARNING_ALLOWED_PROJECTS list.
-# When some of its subdirectories are cleaned up, the subdirectories
-# can be added into ANDROID_WARNING_DISALLOWED_PROJECTS list, e.g.
-# external/fio/.
-ANDROID_WARNING_DISALLOWED_PROJECTS := \
-    art/% \
-    bionic/% \
-    external/fio/% \
-    hardware/interfaces/% \
-
-define find_warning_disallowed_projects
-    $(filter $(ANDROID_WARNING_DISALLOWED_PROJECTS),$(1)/)
-endef
-
-# Projects with compiler warnings are compiled without -Werror.
-ANDROID_WARNING_ALLOWED_PROJECTS := \
-    bootable/% \
-    cts/% \
-    dalvik/% \
-    development/% \
-    device/% \
-    external/% \
-    frameworks/% \
-    hardware/% \
-    packages/% \
-    system/% \
-    test/vts/% \
-    tools/adt/idea/android/ultimate/get_modification_time/jni/% \
-    vendor/% \
-
+# ANDROID_WARNING_ALLOWED_PROJECTS is generated by build/soong.
 define find_warning_allowed_projects
     $(filter $(ANDROID_WARNING_ALLOWED_PROJECTS),$(1)/)
 endef
diff --git a/core/config_sanitizers.mk b/core/config_sanitizers.mk
index 8bd9248..9415143 100644
--- a/core/config_sanitizers.mk
+++ b/core/config_sanitizers.mk
@@ -132,6 +132,12 @@
   my_sanitize_diag := $(filter-out cfi,$(my_sanitize_diag))
 endif
 
+# Disable CFI for host targets
+ifdef LOCAL_IS_HOST_MODULE
+  my_sanitize := $(filter-out cfi,$(my_sanitize))
+  my_sanitize_diag := $(filter-out cfi,$(my_sanitize_diag))
+endif
+
 # Support for local sanitize blacklist paths.
 ifneq ($(my_sanitize)$(my_global_sanitize),)
   ifneq ($(LOCAL_SANITIZE_BLACKLIST),)
diff --git a/core/definitions.mk b/core/definitions.mk
index 1c14f22..c8368b4 100644
--- a/core/definitions.mk
+++ b/core/definitions.mk
@@ -2569,9 +2569,9 @@
 define uncompress-dexs
 $(hide) if (zipinfo $@ '*.dex' 2>/dev/null | grep -v ' stor ' >/dev/null) ; then \
   rm -rf $(dir $@)uncompresseddexs && mkdir $(dir $@)uncompresseddexs; \
-  unzip $@ '*.dex' -d $(dir $@)uncompresseddexs && \
-  zip -d $@ '*.dex' && \
-  ( cd $(dir $@)uncompresseddexs && find . -type f | sort | zip -D -X -0 ../$(notdir $@) -@ ) && \
+  unzip -q $@ '*.dex' -d $(dir $@)uncompresseddexs && \
+  zip -qd $@ '*.dex' && \
+  ( cd $(dir $@)uncompresseddexs && find . -type f | sort | zip -qD -X -0 ../$(notdir $@) -@ ) && \
   rm -rf $(dir $@)uncompresseddexs; \
   fi
 endef
@@ -2581,9 +2581,9 @@
 define uncompress-shared-libs
 $(hide) if (zipinfo $@ $(PRIVATE_EMBEDDED_JNI_LIBS) 2>/dev/null | grep -v ' stor ' >/dev/null) ; then \
   rm -rf $(dir $@)uncompressedlibs && mkdir $(dir $@)uncompressedlibs; \
-  unzip $@ $(PRIVATE_EMBEDDED_JNI_LIBS) -d $(dir $@)uncompressedlibs && \
-  zip -d $@ 'lib/*.so' && \
-  ( cd $(dir $@)uncompressedlibs && find lib -type f | sort | zip -D -X -0 ../$(notdir $@) -@ ) && \
+  unzip -q $@ $(PRIVATE_EMBEDDED_JNI_LIBS) -d $(dir $@)uncompressedlibs && \
+  zip -qd $@ 'lib/*.so' && \
+  ( cd $(dir $@)uncompressedlibs && find lib -type f | sort | zip -qD -X -0 ../$(notdir $@) -@ ) && \
   rm -rf $(dir $@)uncompressedlibs; \
   fi
 endef
diff --git a/core/local_vndk.mk b/core/local_vndk.mk
index 640aac7..3677d40 100644
--- a/core/local_vndk.mk
+++ b/core/local_vndk.mk
@@ -5,10 +5,8 @@
 ifndef LOCAL_SDK_VERSION
   ifneq (,$(filter true,$(LOCAL_VENDOR_MODULE) $(LOCAL_ODM_MODULE) $(LOCAL_OEM_MODULE) $(LOCAL_PROPRIETARY_MODULE)))
     LOCAL_USE_VNDK:=true
-  else
-    ifneq (,$(filter $(TARGET_OUT_VENDOR)%,$(LOCAL_MODULE_PATH) $(LOCAL_MODULE_PATH_32) $(LOCAL_MODULE_PATH_64)))
-      LOCAL_USE_VNDK:=true
-    endif
+    # Note: no need to check LOCAL_MODULE_PATH* since LOCAL_[VENDOR|ODM|OEM]_MODULE is already
+    # set correctly before this is included.
   endif
 endif
 endif
diff --git a/core/prebuilt_internal.mk b/core/prebuilt_internal.mk
index 3fec8d9..47bd1b2 100644
--- a/core/prebuilt_internal.mk
+++ b/core/prebuilt_internal.mk
@@ -216,7 +216,7 @@
     else
       my_coverage_path := $(TARGET_OUT_COVERAGE)/$(patsubst $(PRODUCT_OUT)/%,%,$(my_module_path))
     endif
-    my_coverage_path := $(my_coverage_path)/$(basename $(my_installed_module_stem)).gcnodir
+    my_coverage_path := $(my_coverage_path)/$(patsubst %.so,%,$(my_installed_module_stem)).gcnodir
     $(eval $(call copy-one-file,$(LOCAL_PREBUILT_COVERAGE_ARCHIVE),$(my_coverage_path)))
     $(LOCAL_BUILT_MODULE): $(my_coverage_path)
   endif
diff --git a/target/product/core_minimal.mk b/target/product/core_minimal.mk
index b2ee7bb..05e3b45 100644
--- a/target/product/core_minimal.mk
+++ b/target/product/core_minimal.mk
@@ -159,5 +159,9 @@
     tombstoned.max_tombstone_count=50
 endif
 
+PRODUCT_DEFAULT_PROPERTY_OVERRIDES += \
+    ro.logd.size.stats=64K \
+    log.tag.stats_log=I
+
 $(call inherit-product, $(SRC_TARGET_DIR)/product/runtime_libart.mk)
 $(call inherit-product, $(SRC_TARGET_DIR)/product/base.mk)
diff --git a/tools/releasetools/add_img_to_target_files.py b/tools/releasetools/add_img_to_target_files.py
index 5698356..a882685 100755
--- a/tools/releasetools/add_img_to_target_files.py
+++ b/tools/releasetools/add_img_to_target_files.py
@@ -346,9 +346,15 @@
     cmd.extend(["--include_descriptors_from_image", img_path])
 
 
-def AddVBMeta(output_zip, boot_img_path, system_img_path, vendor_img_path,
-              dtbo_img_path, prefix="IMAGES/"):
-  """Create a VBMeta image and store it in output_zip."""
+def AddVBMeta(output_zip, partitions, prefix="IMAGES/"):
+  """Creates a VBMeta image and store it in output_zip.
+
+  Args:
+    output_zip: The output zip file, which needs to be already open.
+    partitions: A dict that's keyed by partition names with image paths as
+        values. Only valid partition names are accepted, which include 'boot',
+        'recovery', 'system', 'vendor', 'dtbo'.
+  """
   img = OutputFile(output_zip, OPTIONS.input_tmp, prefix, "vbmeta.img")
   if os.path.exists(img.input_name):
     print("vbmeta.img already exists in %s; not rebuilding..." % (prefix,))
@@ -361,10 +367,12 @@
   public_key_dir = tempfile.mkdtemp(prefix="avbpubkey-")
   OPTIONS.tempfiles.append(public_key_dir)
 
-  AppendVBMetaArgsForPartition(cmd, "boot", boot_img_path, public_key_dir)
-  AppendVBMetaArgsForPartition(cmd, "system", system_img_path, public_key_dir)
-  AppendVBMetaArgsForPartition(cmd, "vendor", vendor_img_path, public_key_dir)
-  AppendVBMetaArgsForPartition(cmd, "dtbo", dtbo_img_path, public_key_dir)
+  for partition, path in partitions.items():
+    assert partition in common.AVB_PARTITIONS, 'Unknown partition: %s' % (
+        partition,)
+    assert os.path.exists(path), 'Failed to find %s for partition %s' % (
+        path, partition)
+    AppendVBMetaArgsForPartition(cmd, partition, path, public_key_dir)
 
   args = OPTIONS.info_dict.get("avb_vbmeta_args")
   if args and args.strip():
@@ -481,6 +489,17 @@
 
 
 def AddImagesToTargetFiles(filename):
+  """Creates and adds images (boot/recovery/system/...) to a target_files.zip.
+
+  It works with either a zip file (zip mode), or a directory that contains the
+  files to be packed into a target_files.zip (dir mode). The latter is used when
+  being called from build/make/core/Makefile.
+
+  The images will be created under IMAGES/ in the input target_files.zip.
+
+  Args:
+      filename: the target_files.zip, or the zip root directory.
+  """
   if os.path.isdir(filename):
     OPTIONS.input_tmp = os.path.abspath(filename)
     input_zip = None
@@ -512,10 +531,13 @@
   else:
     OPTIONS.info_dict = common.LoadInfoDict(filename, filename)
     output_zip = None
-    images_dir = os.path.join(OPTIONS.input_tmp, "IMAGES")
-    if not os.path.isdir(images_dir):
-      os.makedirs(images_dir)
-    images_dir = None
+
+  # Always make input_tmp/IMAGES available, since we may stage boot / recovery
+  # images there even under zip mode. The directory will be cleaned up as part
+  # of OPTIONS.input_tmp.
+  images_dir = os.path.join(OPTIONS.input_tmp, "IMAGES")
+  if not os.path.isdir(images_dir):
+    os.makedirs(images_dir)
 
   has_recovery = (OPTIONS.info_dict.get("no_recovery") != "true")
 
@@ -530,6 +552,10 @@
     if fp:
       OPTIONS.info_dict["avb_salt"] = hashlib.sha256(fp).hexdigest()
 
+  # A map between partition names and their paths, which could be used when
+  # generating AVB vbmeta image.
+  partitions = dict()
+
   def banner(s):
     print("\n\n++++ " + s + " ++++\n\n")
 
@@ -539,8 +565,8 @@
       "IMAGES/boot.img", "boot.img", OPTIONS.input_tmp, "BOOT")
   # boot.img may be unavailable in some targets (e.g. aosp_arm64).
   if boot_image:
-    boot_img_path = os.path.join(OPTIONS.input_tmp, "IMAGES", "boot.img")
-    if not os.path.exists(boot_img_path):
+    partitions['boot'] = os.path.join(OPTIONS.input_tmp, "IMAGES", "boot.img")
+    if not os.path.exists(partitions['boot']):
       boot_image.WriteToDir(OPTIONS.input_tmp)
       if output_zip:
         boot_image.AddToZip(output_zip)
@@ -551,9 +577,9 @@
     recovery_image = common.GetBootableImage(
         "IMAGES/recovery.img", "recovery.img", OPTIONS.input_tmp, "RECOVERY")
     assert recovery_image, "Failed to create recovery.img."
-    recovery_img_path = os.path.join(
+    partitions['recovery'] = os.path.join(
         OPTIONS.input_tmp, "IMAGES", "recovery.img")
-    if not os.path.exists(recovery_img_path):
+    if not os.path.exists(partitions['recovery']):
       recovery_image.WriteToDir(OPTIONS.input_tmp)
       if output_zip:
         recovery_image.AddToZip(output_zip)
@@ -572,15 +598,17 @@
           recovery_two_step_image.AddToZip(output_zip)
 
   banner("system")
-  system_img_path = AddSystem(
+  partitions['system'] = system_img_path = AddSystem(
       output_zip, recovery_img=recovery_image, boot_img=boot_image)
-  vendor_img_path = None
+
   if has_vendor:
     banner("vendor")
-    vendor_img_path = AddVendor(output_zip)
+    partitions['vendor'] = vendor_img_path = AddVendor(output_zip)
+
   if has_system_other:
     banner("system_other")
     AddSystemOther(output_zip)
+
   if not OPTIONS.is_signing:
     banner("userdata")
     AddUserdata(output_zip)
@@ -591,15 +619,13 @@
     banner("partition-table")
     AddPartitionTable(output_zip)
 
-  dtbo_img_path = None
   if OPTIONS.info_dict.get("has_dtbo") == "true":
     banner("dtbo")
-    dtbo_img_path = AddDtbo(output_zip)
+    partitions['dtbo'] = AddDtbo(output_zip)
 
   if OPTIONS.info_dict.get("avb_enable") == "true":
     banner("vbmeta")
-    AddVBMeta(output_zip, boot_img_path, system_img_path, vendor_img_path,
-              dtbo_img_path)
+    AddVBMeta(output_zip, partitions)
 
   # For devices using A/B update, copy over images from RADIO/ and/or
   # VENDOR_IMAGES/ to IMAGES/ and make sure we have all the needed
diff --git a/tools/releasetools/blockimgdiff.py b/tools/releasetools/blockimgdiff.py
index 6bca99e..1ef55ff 100644
--- a/tools/releasetools/blockimgdiff.py
+++ b/tools/releasetools/blockimgdiff.py
@@ -1178,42 +1178,10 @@
   def FindTransfers(self):
     """Parse the file_map to generate all the transfers."""
 
-    def AddSplitTransfers(tgt_name, src_name, tgt_ranges, src_ranges,
-                          style, by_id):
-      """Add one or multiple Transfer()s by splitting large files.
-
-      For BBOTA v3, we need to stash source blocks for resumable feature.
-      However, with the growth of file size and the shrink of the cache
-      partition source blocks are too large to be stashed. If a file occupies
-      too many blocks, we split it into smaller pieces by getting multiple
-      Transfer()s.
-
-      The downside is that after splitting, we may increase the package size
-      since the split pieces don't align well. According to our experiments,
-      1/8 of the cache size as the per-piece limit appears to be optimal.
-      Compared to the fixed 1024-block limit, it reduces the overall package
-      size by 30% for volantis, and 20% for angler and bullhead."""
-
-      assert style == "diff"
-      # Possibly split large files into smaller chunks.
+    def AddSplitTransfers(tgt_name, src_name, tgt_ranges, src_ranges, style,
+                          by_id):
+      """Add one or multiple Transfer()s by splitting large files."""
       pieces = 0
-
-      # Change nothing for small files.
-      if (tgt_ranges.size() <= max_blocks_per_transfer and
-          src_ranges.size() <= max_blocks_per_transfer):
-        Transfer(tgt_name, src_name, tgt_ranges, src_ranges,
-                 self.tgt.RangeSha1(tgt_ranges), self.src.RangeSha1(src_ranges),
-                 style, by_id)
-        return
-
-      if tgt_name.split(".")[-1].lower() in ("apk", "jar", "zip"):
-        split_enable = (not self.disable_imgdiff and src_ranges.monotonic and
-                        tgt_ranges.monotonic)
-        if split_enable and (self.tgt.RangeSha1(tgt_ranges) !=
-                             self.src.RangeSha1(src_ranges)):
-          large_apks.append((tgt_name, src_name, tgt_ranges, src_ranges))
-          return
-
       while (tgt_ranges.size() > max_blocks_per_transfer and
              src_ranges.size() > max_blocks_per_transfer):
         tgt_split_name = "%s-%d" % (tgt_name, pieces)
@@ -1239,6 +1207,43 @@
                  self.tgt.RangeSha1(tgt_ranges), self.src.RangeSha1(src_ranges),
                  style, by_id)
 
+    def FindZipsAndAddSplitTransfers(tgt_name, src_name, tgt_ranges,
+                                     src_ranges, style, by_id):
+      """Find all the zip archives and add split transfers for the other files.
+
+      For BBOTA v3, we need to stash source blocks for resumable feature.
+      However, with the growth of file size and the shrink of the cache
+      partition source blocks are too large to be stashed. If a file occupies
+      too many blocks, we split it into smaller pieces by getting multiple
+      Transfer()s.
+
+      The downside is that after splitting, we may increase the package size
+      since the split pieces don't align well. According to our experiments,
+      1/8 of the cache size as the per-piece limit appears to be optimal.
+      Compared to the fixed 1024-block limit, it reduces the overall package
+      size by 30% for volantis, and 20% for angler and bullhead."""
+
+      assert style == "diff"
+
+      # Change nothing for small files.
+      if (tgt_ranges.size() <= max_blocks_per_transfer and
+          src_ranges.size() <= max_blocks_per_transfer):
+        Transfer(tgt_name, src_name, tgt_ranges, src_ranges,
+                 self.tgt.RangeSha1(tgt_ranges), self.src.RangeSha1(src_ranges),
+                 style, by_id)
+        return
+
+      if tgt_name.split(".")[-1].lower() in ("apk", "jar", "zip"):
+        split_enable = (not self.disable_imgdiff and src_ranges.monotonic and
+                        tgt_ranges.monotonic)
+        if split_enable and (self.tgt.RangeSha1(tgt_ranges) !=
+                             self.src.RangeSha1(src_ranges)):
+          large_apks.append((tgt_name, src_name, tgt_ranges, src_ranges))
+          return
+
+      AddSplitTransfers(tgt_name, src_name, tgt_ranges, src_ranges,
+                        style, by_id)
+
     def AddTransfer(tgt_name, src_name, tgt_ranges, src_ranges, style, by_id,
                     split=False):
       """Wrapper function for adding a Transfer()."""
@@ -1287,7 +1292,7 @@
           assert tgt_changed + tgt_skipped.size() == tgt_size
           print('%10d %10d (%6.2f%%) %s' % (tgt_skipped.size(), tgt_size,
                 tgt_skipped.size() * 100.0 / tgt_size, tgt_name))
-          AddSplitTransfers(
+          FindZipsAndAddSplitTransfers(
               "%s-skipped" % (tgt_name,),
               "%s-skipped" % (src_name,),
               tgt_skipped, src_skipped, style, by_id)
@@ -1304,7 +1309,7 @@
             return
 
       # Add the transfer(s).
-      AddSplitTransfers(
+      FindZipsAndAddSplitTransfers(
           tgt_name, src_name, tgt_ranges, src_ranges, style, by_id)
 
     def ParseAndValidateSplitInfo(patch_size, tgt_ranges, src_ranges,
@@ -1403,10 +1408,13 @@
                src_file, tgt_file, patch_file]
         p = common.Run(cmd, stdout=subprocess.PIPE)
         p.communicate()
-        # TODO(xunchang) fall back to the normal split if imgdiff fails.
         if p.returncode != 0:
-          raise ValueError("Failed to create patch between {} and {}".format(
-              src_name, tgt_name))
+          print("Failed to create patch between {} and {},"
+                " falling back to bsdiff".format(src_name, tgt_name))
+          with transfer_lock:
+            AddSplitTransfers(tgt_name, src_name, tgt_ranges, src_ranges,
+                              "diff", self.transfers)
+          continue
 
         with open(patch_info_file) as patch_info:
           lines = patch_info.readlines()
diff --git a/tools/releasetools/check_ota_package_signature.py b/tools/releasetools/check_ota_package_signature.py
index 1f8b7bb..8106d06 100755
--- a/tools/releasetools/check_ota_package_signature.py
+++ b/tools/releasetools/check_ota_package_signature.py
@@ -22,7 +22,10 @@
 
 import argparse
 import common
+import os
+import os.path
 import re
+import site
 import subprocess
 import sys
 import tempfile
@@ -32,7 +35,12 @@
 from hashlib import sha256
 
 # 'update_payload' package is under 'system/update_engine/scripts/', which
-# should to be included in PYTHONPATH.
+# should be included in PYTHONPATH. Try to set it up automatically if
+# if ANDROID_BUILD_TOP is available.
+top = os.getenv('ANDROID_BUILD_TOP')
+if top:
+  site.addsitedir(os.path.join(top, 'system', 'update_engine', 'scripts'))
+
 from update_payload.payload import Payload
 from update_payload.update_metadata_pb2 import Signatures
 
diff --git a/tools/releasetools/common.py b/tools/releasetools/common.py
index f80d0ec..75c86cc 100644
--- a/tools/releasetools/common.py
+++ b/tools/releasetools/common.py
@@ -452,10 +452,12 @@
   else:
     cmd.extend(["--output", img.name])
 
+  # "boot" or "recovery", without extension.
+  partition_name = os.path.basename(sourcedir).lower()
+
   p = Run(cmd, stdout=subprocess.PIPE)
   p.communicate()
-  assert p.returncode == 0, "mkbootimg of %s image failed" % (
-      os.path.basename(sourcedir),)
+  assert p.returncode == 0, "mkbootimg of %s image failed" % (partition_name,)
 
   if (info_dict.get("boot_signer", None) == "true" and
       info_dict.get("verity_key", None)):
@@ -464,7 +466,7 @@
     if two_step_image:
       path = "/boot"
     else:
-      path = "/" + os.path.basename(sourcedir).lower()
+      path = "/" + partition_name
     cmd = [OPTIONS.boot_signer_path]
     cmd.extend(OPTIONS.boot_signer_args)
     cmd.extend([path, img.name,
@@ -476,7 +478,7 @@
 
   # Sign the image if vboot is non-empty.
   elif info_dict.get("vboot", None):
-    path = "/" + os.path.basename(sourcedir).lower()
+    path = "/" + partition_name
     img_keyblock = tempfile.NamedTemporaryFile()
     # We have switched from the prebuilt futility binary to using the tool
     # (futility-host) built from the source. Override the setting in the old
@@ -503,15 +505,16 @@
     avbtool = os.getenv('AVBTOOL') or info_dict["avb_avbtool"]
     part_size = info_dict["boot_size"]
     cmd = [avbtool, "add_hash_footer", "--image", img.name,
-           "--partition_size", str(part_size), "--partition_name", "boot"]
-    AppendAVBSigningArgs(cmd, "boot")
+           "--partition_size", str(part_size), "--partition_name",
+           partition_name]
+    AppendAVBSigningArgs(cmd, partition_name)
     args = info_dict.get("avb_boot_add_hash_footer_args")
     if args and args.strip():
       cmd.extend(shlex.split(args))
     p = Run(cmd, stdout=subprocess.PIPE)
     p.communicate()
     assert p.returncode == 0, "avbtool add_hash_footer of %s failed" % (
-        os.path.basename(OPTIONS.input_tmp))
+        partition_name,)
 
   img.seek(os.SEEK_SET, 0)
   data = img.read()
diff --git a/tools/signtos/Android.bp b/tools/signtos/Android.bp
new file mode 100644
index 0000000..b26631f
--- /dev/null
+++ b/tools/signtos/Android.bp
@@ -0,0 +1,27 @@
+//
+// Copyright (C) 2014 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+// the signtos tool - signs Trusty images
+// ============================================================
+java_library_host {
+    name: "signtos",
+    srcs: ["SignTos.java"],
+    manifest: "SignTos.mf",
+    static_libs: [
+        "bouncycastle",
+        "bouncycastle-bcpkix",
+    ],
+}
diff --git a/tools/signtos/Android.mk b/tools/signtos/Android.mk
deleted file mode 100644
index 3e869b3..0000000
--- a/tools/signtos/Android.mk
+++ /dev/null
@@ -1,25 +0,0 @@
-#
-# Copyright (C) 2014 The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-LOCAL_PATH := $(call my-dir)
-
-# the signtos tool - signs Trusty images
-# ============================================================
-include $(CLEAR_VARS)
-LOCAL_MODULE := signtos
-LOCAL_SRC_FILES := SignTos.java
-LOCAL_JAR_MANIFEST := SignTos.mf
-LOCAL_STATIC_JAVA_LIBRARIES := bouncycastle bouncycastle-bcpkix
-include $(BUILD_HOST_JAVA_LIBRARY)