Merge "Allow vendors to add custom vbmeta partitions"
diff --git a/OWNERS b/OWNERS
index 5c7f5ad..57d8994 100644
--- a/OWNERS
+++ b/OWNERS
@@ -3,6 +3,7 @@
 # Since this file affects all Android developers, lock it down. There is still
 # round the world timzeone coverage.
 per-file envsetup.sh = joeo@google.com, jingwen@google.com, lberki@google.com
+per-file shell_utils.sh = joeo@google.com, jingwen@google.com, lberki@google.com
 
 # Finalization scripts
 per-file finalize* = smoreland@google.com, alexbuy@google.com
diff --git a/core/Makefile b/core/Makefile
index 3f01050..6f11590 100644
--- a/core/Makefile
+++ b/core/Makefile
@@ -3492,6 +3492,18 @@
   INTERNAL_VENDORIMAGE_FILES += $(call create-partition-compat-symlink,$(TARGET_OUT_VENDOR)/lib/modules,/vendor_dlkm/lib/modules,vendor_dlkm.img)
 endif
 
+# Install vendor/etc/linker.config.pb when PRODUCT_VENDOR_LINKER_CONFIG_FRAGMENTS is set
+ifneq ($(strip $(PRODUCT_VENDOR_LINKER_CONFIG_FRAGMENTS)),)
+vendor_linker_config_file := $(TARGET_OUT_VENDOR)/etc/linker.config.pb
+$(vendor_linker_config_file): private_linker_config_fragments := $(PRODUCT_VENDOR_LINKER_CONFIG_FRAGMENTS)
+$(vendor_linker_config_file): $(PRODUCT_VENDOR_LINKER_CONFIG_FRAGMENTS) | $(HOST_OUT_EXECUTABLES)/conv_linker_config
+	$(HOST_OUT_EXECUTABLES)/conv_linker_config proto \
+		--source $(call normalize-path-list,$(private_linker_config_fragments)) \
+		--output $@
+$(call define declare-0p-target,$(vendor_linker_config_file),)
+INTERNAL_VENDORIMAGE_FILES += $(vendor_linker_config_file)
+endif
+
 INSTALLED_FILES_FILE_VENDOR := $(PRODUCT_OUT)/installed-files-vendor.txt
 INSTALLED_FILES_JSON_VENDOR := $(INSTALLED_FILES_FILE_VENDOR:.txt=.json)
 $(INSTALLED_FILES_FILE_VENDOR): .KATI_IMPLICIT_OUTPUTS := $(INSTALLED_FILES_JSON_VENDOR)
@@ -3972,12 +3984,16 @@
 INSTALLED_PVMFW_BINARY_TARGET := $(call module-installed-files,pvmfw_bin)
 INTERNAL_PVMFWIMAGE_FILES := $(call module-target-built-files,pvmfw_img)
 INTERNAL_PVMFW_EMBEDDED_AVBKEY := $(call module-target-built-files,pvmfw_embedded_key)
+INTERNAL_PVMFW_SYMBOL := $(TARGET_OUT_EXECUTABLES_UNSTRIPPED)/pvmfw
 
 $(call declare-1p-container,$(INSTALLED_PVMFWIMAGE_TARGET),)
 $(call declare-container-license-deps,$(INSTALLED_PVMFWIMAGE_TARGET),$(INTERNAL_PVMFWIMAGE_FILES),$(PRODUCT_OUT)/:/)
 
 UNMOUNTED_NOTICE_VENDOR_DEPS += $(INSTALLED_PVMFWIMAGE_TARGET)
 
+# Place the unstripped pvmfw image to the symbols directory
+$(INTERNAL_PVMFWIMAGE_FILES): |$(INTERNAL_PVMFW_SYMBOL)
+
 $(eval $(call copy-one-file,$(INTERNAL_PVMFWIMAGE_FILES),$(INSTALLED_PVMFWIMAGE_TARGET)))
 
 $(INSTALLED_PVMFWIMAGE_TARGET): $(INSTALLED_PVMFW_EMBEDDED_AVBKEY_TARGET)
@@ -4618,6 +4634,7 @@
     $(INTERNAL_VENDOR_DLKMIMAGE_FILES) \
     $(INTERNAL_ODM_DLKMIMAGE_FILES) \
     $(INTERNAL_SYSTEM_DLKMIMAGE_FILES) \
+    $(INTERNAL_PVMFWIMAGE_FILES) \
 
 # -----------------------------------------------------------------
 # Check VINTF of build
@@ -4630,35 +4647,39 @@
 
 APEX_OUT := $(PRODUCT_OUT)/apex
 # -----------------------------------------------------------------
-# Create apex-info-file.xsd
+# Create apex-info-file.xml
 
-APEX_DIRS := \
+apex_dirs := \
   $(TARGET_OUT)/apex/% \
   $(TARGET_OUT_SYSTEM_EXT)/apex/% \
   $(TARGET_OUT_VENDOR)/apex/% \
   $(TARGET_OUT_ODM)/apex/% \
   $(TARGET_OUT_PRODUCT)/apex/% \
 
-apex_vintf_files := $(sort $(filter $(APEX_DIRS), $(INTERNAL_ALLIMAGES_FILES)))
-APEX_INFO_FILE   := $(APEX_OUT)/apex-info-list.xml
+apex_files := $(sort $(filter $(apex_dirs), $(INTERNAL_ALLIMAGES_FILES)))
+APEX_INFO_FILE := $(APEX_OUT)/apex-info-list.xml
 
-$(APEX_INFO_FILE): $(HOST_OUT_EXECUTABLES)/dump_apex_info $(apex_vintf_files)
+# dump_apex_info scans $(PRODUCT_OUT)/apex and writes apex-info-list.xml there.
+# This relies on the fact that rules for .apex files install the contents in $(PRODUCT_OUT)/apex.
+$(APEX_INFO_FILE): $(HOST_OUT_EXECUTABLES)/dump_apex_info $(apex_files)
 	@echo "Creating apex-info-file in $(PRODUCT_OUT) "
 	$< --root_dir $(PRODUCT_OUT)
 
-apex_vintf_files :=
+apex_files :=
+apex_dirs :=
 
 # The build system only writes VINTF metadata to */etc/vintf paths. Legacy paths aren't needed here
 # because they are only used for prebuilt images.
+# APEX files in /vendor/apex can have VINTF fragments as well.
 check_vintf_common_srcs_patterns := \
   $(TARGET_OUT)/etc/vintf/% \
   $(TARGET_OUT_VENDOR)/etc/vintf/% \
   $(TARGET_OUT_ODM)/etc/vintf/% \
   $(TARGET_OUT_PRODUCT)/etc/vintf/% \
   $(TARGET_OUT_SYSTEM_EXT)/etc/vintf/% \
+  $(TARGET_OUT_VENDOR)/apex/% \
 
 check_vintf_common_srcs := $(sort $(filter $(check_vintf_common_srcs_patterns),$(INTERNAL_ALLIMAGES_FILES)))
-check_vintf_common_srcs += $(APEX_INFO_FILE)
 check_vintf_common_srcs_patterns :=
 
 check_vintf_has_system :=
@@ -4699,7 +4720,8 @@
 
 # -- Check vendor manifest / matrix including fragments (excluding other device manifests / matrices)
 check_vintf_vendor_deps := $(filter $(TARGET_OUT_VENDOR)/etc/vintf/%, $(check_vintf_common_srcs))
-ifneq ($(check_vintf_vendor_deps),)
+check_vintf_vendor_deps += $(filter $(TARGET_OUT_VENDOR)/apex/%, $(check_vintf_common_srcs))
+ifneq ($(strip $(check_vintf_vendor_deps)),)
 check_vintf_has_vendor := true
 check_vintf_vendor_log := $(intermediates)/check_vintf_vendor.log
 check_vintf_all_deps += $(check_vintf_vendor_log)
@@ -4710,9 +4732,9 @@
   $(if $(DEVICE_MANIFEST_FILE),EMPTY_VENDOR_SKU_PLACEHOLDER,\
     $(if $(DEVICE_MANIFEST_SKUS),,EMPTY_VENDOR_SKU_PLACEHOLDER)) \
   $(DEVICE_MANIFEST_SKUS)
-$(check_vintf_vendor_log): $(HOST_OUT_EXECUTABLES)/checkvintf $(check_vintf_vendor_deps)
+$(check_vintf_vendor_log): $(HOST_OUT_EXECUTABLES)/checkvintf $(check_vintf_vendor_deps) $(APEX_INFO_FILE)
 	$(foreach vendor_sku,$(PRIVATE_VENDOR_SKUS), \
-	  ( $< --check-one --dirmap /vendor:$(TARGET_OUT_VENDOR) \
+	  ( $< --check-one --dirmap /vendor:$(TARGET_OUT_VENDOR) --dirmap /apex:$(APEX_OUT) \
 	       --property ro.boot.product.vendor.sku=$(filter-out EMPTY_VENDOR_SKU_PLACEHOLDER,$(vendor_sku)) \
 	       > $@ 2>&1 ) || ( cat $@ && exit 1 ); )
 $(call declare-0p-target,$(check_vintf_vendor_log))
@@ -4826,7 +4848,7 @@
 check_vintf_all_deps += $(check_vintf_compatible_log)
 
 check_vintf_compatible_args :=
-check_vintf_compatible_deps := $(check_vintf_common_srcs)
+check_vintf_compatible_deps := $(check_vintf_common_srcs) $(APEX_INFO_FILE)
 
 ifeq ($(PRODUCT_OTA_ENFORCE_VINTF_KERNEL_REQUIREMENTS),true)
 ifneq (,$(BUILT_KERNEL_VERSION_FILE)$(BUILT_KERNEL_CONFIGS_FILE))
diff --git a/core/android_soong_config_vars.mk b/core/android_soong_config_vars.mk
index 0cd73ae..bf113ee 100644
--- a/core/android_soong_config_vars.mk
+++ b/core/android_soong_config_vars.mk
@@ -87,6 +87,10 @@
 # Apex build mode variables
 ifdef APEX_BUILD_FOR_PRE_S_DEVICES
 $(call add_soong_config_var_value,ANDROID,library_linking_strategy,prefer_static)
+else
+ifdef KEEP_APEX_INHERIT
+$(call add_soong_config_var_value,ANDROID,library_linking_strategy,prefer_static)
+endif
 endif
 
 ifeq (true,$(MODULE_BUILD_FROM_SOURCE))
diff --git a/core/dex_preopt.mk b/core/dex_preopt.mk
index d7a00d0..88ec47f 100644
--- a/core/dex_preopt.mk
+++ b/core/dex_preopt.mk
@@ -64,10 +64,22 @@
 bootclasspath_jars := $(DEXPREOPT_BOOTCLASSPATH_DEX_FILES)
 
 # TODO remove system_server_jars usages from boot.zip and depend directly on system_server.zip file.
+
+# Use "/system" path for JARs with "platform:" prefix.
+# These JARs counterintuitively use "platform" prefix but they will
+# be actually installed to /system partition.
+platform_system_server_jars = $(filter platform:%, $(PRODUCT_SYSTEM_SERVER_JARS))
 system_server_jars := \
-  $(foreach m,$(PRODUCT_SYSTEM_SERVER_JARS),\
+  $(foreach m,$(platform_system_server_jars),\
     $(PRODUCT_OUT)/system/framework/$(call word-colon,2,$(m)).jar)
 
+# For the remaining system server JARs use the partition signified by the prefix.
+# For example, prefix "system_ext:" will use "/system_ext" path.
+other_system_server_jars = $(filter-out $(platform_system_server_jars), $(PRODUCT_SYSTEM_SERVER_JARS))
+system_server_jars += \
+  $(foreach m,$(other_system_server_jars),\
+    $(PRODUCT_OUT)/$(call word-colon,1,$(m))/framework/$(call word-colon,2,$(m)).jar)
+
 $(boot_zip): PRIVATE_BOOTCLASSPATH_JARS := $(bootclasspath_jars)
 $(boot_zip): PRIVATE_SYSTEM_SERVER_JARS := $(system_server_jars)
 $(boot_zip): $(bootclasspath_jars) $(system_server_jars) $(SOONG_ZIP) $(MERGE_ZIPS) $(DEXPREOPT_IMAGE_ZIP_boot) $(DEXPREOPT_IMAGE_ZIP_art)
diff --git a/core/product.mk b/core/product.mk
index 7621c71..3b22314 100644
--- a/core/product.mk
+++ b/core/product.mk
@@ -373,6 +373,9 @@
 # If true, installs a full version of com.android.virt APEX.
 _product_single_value_vars += PRODUCT_AVF_ENABLED
 
+# List of .json files to be merged/compiled into vendor/etc/linker.config.pb
+_product_list_vars += PRODUCT_VENDOR_LINKER_CONFIG_FRAGMENTS
+
 # Whether to use userfaultfd GC.
 # Possible values are:
 # - "default" or empty: both the build system and the runtime determine whether to use userfaultfd
diff --git a/core/product_config.rbc b/core/product_config.rbc
index b0d6977..da8209b 100644
--- a/core/product_config.rbc
+++ b/core/product_config.rbc
@@ -59,6 +59,12 @@
         if _options.format == "pretty":
             print(attr, "=", repr(value))
         elif _options.format == "make":
+            value = list(value)
+            for i, x in enumerate(value):
+                if type(x) == "tuple" and len(x) == 1:
+                    value[i] = "@inherit:" + x[0] + ".mk"
+                elif type(x) != "string":
+                    fail("Wasn't a list of strings:", attr, " value:", value)
             print(attr, ":=", " ".join(value))
     elif _options.format == "pretty":
         print(attr, "=", repr(value))
diff --git a/core/soong_config.mk b/core/soong_config.mk
index a89db4f..e6c4d64 100644
--- a/core/soong_config.mk
+++ b/core/soong_config.mk
@@ -249,9 +249,9 @@
 $(call add_json_list, MissingUsesLibraries,              $(INTERNAL_PLATFORM_MISSING_USES_LIBRARIES))
 
 $(call add_json_map, VendorVars)
-$(foreach namespace,$(SOONG_CONFIG_NAMESPACES),\
+$(foreach namespace,$(sort $(SOONG_CONFIG_NAMESPACES)),\
   $(call add_json_map, $(namespace))\
-  $(foreach key,$(SOONG_CONFIG_$(namespace)),\
+  $(foreach key,$(sort $(SOONG_CONFIG_$(namespace))),\
     $(call add_json_str,$(key),$(subst ",\",$(SOONG_CONFIG_$(namespace)_$(key)))))\
   $(call end_json_map))
 $(call end_json_map)
diff --git a/core/tasks/vendor_snapshot.mk b/core/tasks/vendor_snapshot.mk
index d1849ab..83c1379 100644
--- a/core/tasks/vendor_snapshot.mk
+++ b/core/tasks/vendor_snapshot.mk
@@ -27,56 +27,6 @@
 
 $(call dist-for-goals, vendor-fake-snapshot, $(SOONG_VENDOR_FAKE_SNAPSHOT_ZIP):fake/$(notdir $(SOONG_VENDOR_FAKE_SNAPSHOT_ZIP)))
 
-# Capture prebuilt vendor static libraries of hwasan variant.
-# To build the hwasan variant `SANITIZE_TARGET=hwaddress` must be set.
-# vendor-hwasan-snapshot goal zips hwasan static libs listed in
-# PRODUCT_VSDK_HWASAN_STATIC_PATHS which has a list of pairs of
-# 'module name':'source directory path'
-ifeq ($(SANITIZE_TARGET),hwaddress)
-
-vsdk_hwasan_static_zip := $(PRODUCT_OUT)/vsdk-hwasan-snapshot.zip
-vsdk_hwasan_static_dir := $(PRODUCT_OUT)/vsdk-hwasan-snapshot
-vsdk_hwasan_variants := \
-	android \
-	vendor.$(PLATFORM_VNDK_VERSION) \
-	$(TARGET_ARCH) \
-	$(TARGET_ARCH_VARIANT) \
-	$(TARGET_CPU_VARIANT) \
-	static \
-	hwasan
-vsdk_hwasan_variant_name := $(subst _generic_,_,$(subst $(space),_,$(vsdk_hwasan_variants)))
-
-define get_vendor_hwasan_static_path
-$(SOONG_OUT_DIR)/.intermediates/$(call word-colon,2,$(1))/$(call word-colon,1,$(1))/$(vsdk_hwasan_variant_name)/$(call word-colon,1,$(1)).a
-endef
-
-$(vsdk_hwasan_static_zip): PRIVATE_MAKEFILE := $(current_makefile)
-$(vsdk_hwasan_static_zip): PRIVATE_HWASAN_DIR := $(vsdk_hwasan_static_dir)
-$(vsdk_hwasan_static_zip): $(SOONG_ZIP) $(foreach p, $(PRODUCT_VSDK_HWASAN_STATIC_PATHS), $(call get_vendor_hwasan_static_path,$(p)))
-	$(if $(PRODUCT_VSDK_HWASAN_STATIC_PATHS),,\
-		$(call echo-error,$(PRIVATE_MAKEFILE),\
-			"CANNOT generate Vendor HWASAN snapshot. PRODUCT_VSDK_HWASAN_STATIC_PATHS is not defined.") &&\
-			exit 1)
-	@rm -rf $(PRIVATE_HWASAN_DIR)
-	@mkdir -p $(PRIVATE_HWASAN_DIR)
-	$(foreach p, $(PRODUCT_VSDK_HWASAN_STATIC_PATHS), \
-		cp -f $(call get_vendor_hwasan_static_path,$(p)) $(PRIVATE_HWASAN_DIR) &&) true
-	$(SOONG_ZIP) -o $@ -C $(PRIVATE_HWASAN_DIR) -D $(PRIVATE_HWASAN_DIR)
-
-.PHONY: vendor-hwasan-snapshot
-vendor-hwasan-snapshot: $(vsdk_hwasan_static_zip)
-
-$(call dist-for-goals, vendor-hwasan-snapshot, $(vsdk_hwasan_static_zip))
-
-else # Not for the HWASAN build
-.PHONY: vendor-hwasan-snapshot
-vendor-hwasan-snapshot: PRIVATE_MAKEFILE := $(current_makefile)
-vendor-hwasan-snapshot:
-	$(call echo-error,$(PRIVATE_MAKEFILE),\
-		"CANNOT generate Vendor HWASAN snapshot. SANITIZE_TARGET must be set to 'hwaddress'.")
-	exit 1
-endif # SANITIZE_TARGET
-
 else # BOARD_VNDK_VERSION is NOT set to 'current'
 
 .PHONY: vendor-snapshot
@@ -93,10 +43,4 @@
 		"CANNOT generate Vendor snapshot. BOARD_VNDK_VERSION must be set to 'current'.")
 	exit 1
 
-.PHONY: vendor-hwasan-snapshot
-vendor-hwasan-snapshot: PRIVATE_MAKEFILE := $(current_makefile)
-	$(call echo-error,$(PRIVATE_MAKEFILE),\
-		"CANNOT generate Vendor HWASAN snapshot. BOARD_VNDK_VERSION must be set to 'current'.")
-	exit 1
-
 endif # BOARD_VNDK_VERSION
diff --git a/core/version_defaults.mk b/core/version_defaults.mk
index 734e32b..e6a96ff 100644
--- a/core/version_defaults.mk
+++ b/core/version_defaults.mk
@@ -103,7 +103,7 @@
     #  It must be of the form "YYYY-MM-DD" on production devices.
     #  It must match one of the Android Security Patch Level strings of the Public Security Bulletins.
     #  If there is no $PLATFORM_SECURITY_PATCH set, keep it empty.
-    PLATFORM_SECURITY_PATCH := 2022-12-05
+    PLATFORM_SECURITY_PATCH := 2023-01-05
 endif
 
 include $(BUILD_SYSTEM)/version_util.mk
diff --git a/envsetup.sh b/envsetup.sh
index 4990800..a30f6bd 100644
--- a/envsetup.sh
+++ b/envsetup.sh
@@ -1,3 +1,55 @@
+# Copyright (C) 2022 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.
+
+# gettop is duplicated here and in shell_utils.mk, because it's difficult
+# to find shell_utils.make without it for all the novel ways this file can be
+# sourced.  Other common functions should only be in one place or the other.
+function _gettop_once
+{
+    local TOPFILE=build/make/core/envsetup.mk
+    if [ -n "$TOP" -a -f "$TOP/$TOPFILE" ] ; then
+        # The following circumlocution ensures we remove symlinks from TOP.
+        (cd "$TOP"; PWD= /bin/pwd)
+    else
+        if [ -f $TOPFILE ] ; then
+            # The following circumlocution (repeated below as well) ensures
+            # that we record the true directory name and not one that is
+            # faked up with symlink names.
+            PWD= /bin/pwd
+        else
+            local HERE=$PWD
+            local T=
+            while [ \( ! \( -f $TOPFILE \) \) -a \( "$PWD" != "/" \) ]; do
+                \cd ..
+                T=`PWD= /bin/pwd -P`
+            done
+            \cd "$HERE"
+            if [ -f "$T/$TOPFILE" ]; then
+                echo "$T"
+            fi
+        fi
+    fi
+}
+T=$(_gettop_once)
+if [ ! "$T" ]; then
+    echo "Couldn't locate the top of the tree. Always source build/envsetup.sh from the root of the tree." >&2
+    return 1
+fi
+IMPORTING_ENVSETUP=true source $T/build/make/shell_utils.sh
+
+
+# Help
 function hmm() {
 cat <<EOF
 
@@ -928,33 +980,6 @@
     destroy_build_var_cache
 }
 
-function gettop
-{
-    local TOPFILE=build/make/core/envsetup.mk
-    if [ -n "$TOP" -a -f "$TOP/$TOPFILE" ] ; then
-        # The following circumlocution ensures we remove symlinks from TOP.
-        (cd "$TOP"; PWD= /bin/pwd)
-    else
-        if [ -f $TOPFILE ] ; then
-            # The following circumlocution (repeated below as well) ensures
-            # that we record the true directory name and not one that is
-            # faked up with symlink names.
-            PWD= /bin/pwd
-        else
-            local HERE=$PWD
-            local T=
-            while [ \( ! \( -f $TOPFILE \) \) -a \( "$PWD" != "/" \) ]; do
-                \cd ..
-                T=`PWD= /bin/pwd -P`
-            done
-            \cd "$HERE"
-            if [ -f "$T/$TOPFILE" ]; then
-                echo "$T"
-            fi
-        fi
-    fi
-}
-
 # TODO: Merge into gettop as part of launching multitree
 function multitree_gettop
 {
diff --git a/shell_utils.sh b/shell_utils.sh
new file mode 100644
index 0000000..9de5a50
--- /dev/null
+++ b/shell_utils.sh
@@ -0,0 +1,74 @@
+# Copyright (C) 2022 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.
+
+function gettop
+{
+    local TOPFILE=build/make/core/envsetup.mk
+    # The ${TOP-} expansion allows this to work even with set -u
+    if [ -n "${TOP:-}" -a -f "${TOP:-}/$TOPFILE" ] ; then
+        # The following circumlocution ensures we remove symlinks from TOP.
+        (cd "$TOP"; PWD= /bin/pwd)
+    else
+        if [ -f $TOPFILE ] ; then
+            # The following circumlocution (repeated below as well) ensures
+            # that we record the true directory name and not one that is
+            # faked up with symlink names.
+            PWD= /bin/pwd
+        else
+            local HERE=$PWD
+            local T=
+            while [ \( ! \( -f $TOPFILE \) \) -a \( "$PWD" != "/" \) ]; do
+                \cd ..
+                T=`PWD= /bin/pwd -P`
+            done
+            \cd "$HERE"
+            if [ -f "$T/$TOPFILE" ]; then
+                echo "$T"
+            fi
+        fi
+    fi
+}
+
+# Sets TOP, or if the root of the tree can't be found, prints a message and
+# exits.  Since this function exits, it should not be called from functions
+# defined in envsetup.sh.
+if [ -z "${IMPORTING_ENVSETUP:-}" ] ; then
+function require_top
+{
+    TOP=$(gettop)
+    if [[ ! $TOP ]] ; then
+        echo "Can not locate root of source tree. $(basename $0) must be run from within the Android source tree." >&2
+        exit 1
+    fi
+}
+fi
+
+function getoutdir
+{
+    local top=$(gettop)
+    local out_dir="${OUT_DIR:-}"
+    if [[ -z "${out_dir}" ]]; then
+        if [[ -n "${OUT_DIR_COMMON_BASE:-}" && -n "${top}" ]]; then
+            out_dir="${OUT_DIR_COMMON_BASE}/$(basename ${top})"
+        else
+            out_dir="out"
+        fi
+    fi
+    if [[ "${out_dir}" != /* ]]; then
+        out_dir="${top}/${out_dir}"
+    fi
+    echo "${out_dir}"
+}
+
+
diff --git a/target/product/module_common.mk b/target/product/module_common.mk
index 54f3949..ec670ee 100644
--- a/target/product/module_common.mk
+++ b/target/product/module_common.mk
@@ -25,3 +25,8 @@
 # Builds using a module product should build modules from source, even if
 # BRANCH_DEFAULT_MODULE_BUILD_FROM_SOURCE says otherwise.
 PRODUCT_MODULE_BUILD_FROM_SOURCE := true
+
+# Build sdk from source if the branch is not using slim manifests.
+ifneq (,$(strip $(wildcard frameworks/base/Android.bp)))
+  UNBUNDLED_BUILD_SDKS_FROM_SOURCE := true
+endif
diff --git a/target/product/runtime_libart.mk b/target/product/runtime_libart.mk
index a62cda7..bd4fd1c 100644
--- a/target/product/runtime_libart.mk
+++ b/target/product/runtime_libart.mk
@@ -95,7 +95,6 @@
 # The thermal cutoff value is currently set to THERMAL_STATUS_MODERATE.
 PRODUCT_SYSTEM_PROPERTIES += \
     dalvik.vm.usejit=true \
-    dalvik.vm.usejitprofiles=true \
     dalvik.vm.dexopt.secondary=true \
     dalvik.vm.dexopt.thermal-cutoff=2 \
     dalvik.vm.appimageformat=lz4
diff --git a/tests/b_tests.sh b/tests/b_tests.sh
index 45cb4f7..13f156d 100755
--- a/tests/b_tests.sh
+++ b/tests/b_tests.sh
@@ -27,6 +27,10 @@
 b build "$test_target" --run-soong-tests
 b build --run-soong-tests "$test_target"
 b --run-soong-tests build "$test_target"
+# Test that the bazel server can be restarted once shut down. If run in a
+# docker container, you need to run the docker container with --init or
+# have some other process as PID 1 that can reap zombies.
+b shutdown
 b cquery 'kind(test, //build/bazel/examples/android_app/...)' --config=android
 b run $test_target -- --help >/dev/null
 
diff --git a/tests/inherits_in_regular_variables/inherit1.rbc b/tests/inherits_in_regular_variables/inherit1.rbc
new file mode 100644
index 0000000..4ce8825
--- /dev/null
+++ b/tests/inherits_in_regular_variables/inherit1.rbc
@@ -0,0 +1,21 @@
+# Copyright 2023 Google LLC
+#
+# 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
+#
+#      https://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.
+
+load("//build/make/core:product_config.rbc", "rblf")
+
+def init(g, handle):
+  cfg = rblf.cfg(handle)
+
+  cfg.setdefault("PRODUCT_PACKAGES", [])
+  cfg["PRODUCT_PACKAGES"] += ["bar"]
diff --git a/tests/inherits_in_regular_variables/product.rbc b/tests/inherits_in_regular_variables/product.rbc
new file mode 100644
index 0000000..c193c65
--- /dev/null
+++ b/tests/inherits_in_regular_variables/product.rbc
@@ -0,0 +1,27 @@
+# Copyright 2023 Google LLC
+#
+# 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
+#
+#      https://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.
+
+load("//build/make/core:product_config.rbc", "rblf")
+load(":inherit1.rbc", _inherit1_init = "init")
+
+def init(g, handle):
+  cfg = rblf.cfg(handle)
+
+  cfg.setdefault("PRODUCT_PACKAGES", [])
+  cfg["PRODUCT_PACKAGES"] += ["foo"]
+
+  g["PRODUCT_PACKAGES_COPY"] = cfg["PRODUCT_PACKAGES"]
+
+  rblf.inherit(handle, "test/inherit1", _inherit1_init)
+
diff --git a/tests/inherits_in_regular_variables/test.rbc b/tests/inherits_in_regular_variables/test.rbc
new file mode 100644
index 0000000..3a76d8a
--- /dev/null
+++ b/tests/inherits_in_regular_variables/test.rbc
@@ -0,0 +1,30 @@
+# Copyright 2023 Google LLC
+#
+# 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
+#
+#      https://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.
+
+load("//build/make/core:product_config.rbc", "rblf")
+load("//build/make/tests/input_variables.rbc", input_variables_init = "init")
+load(":product.rbc", "init")
+
+
+def assert_eq(expected, actual):
+    if expected != actual:
+        fail("Expected '%s', got '%s'" % (expected, actual))
+
+def test():
+    (globals, globals_base) = rblf.product_configuration("test/device", init, input_variables_init)
+    assert_eq(["foo", "bar"], globals["PRODUCTS.test/device.mk.PRODUCT_PACKAGES"])
+    assert_eq(["foo", ("test/inherit1",)], globals["PRODUCT_PACKAGES_COPY"])
+
+    # Ideally we would check that rblf.printvars returns the correct result, but we don't have
+    # a good way to intercept its output or mock rblf_cli
diff --git a/tests/run.rbc b/tests/run.rbc
index e8c4caa..1b51719 100644
--- a/tests/run.rbc
+++ b/tests/run.rbc
@@ -28,6 +28,7 @@
 load("//build/make/tests/single_value_inheritance:test.rbc", test_single_value_inheritance = "test")
 load("//build/make/tests/artifact_path_requirements:test.rbc", test_artifact_path_requirements = "test")
 load("//build/make/tests/prefixed_sort_order:test.rbc", test_prefixed_sort_order = "test")
+load("//build/make/tests/inherits_in_regular_variables:test.rbc", test_inherits_in_regular_variables = "test")
 
 def assert_eq(expected, actual):
     if expected != actual:
@@ -176,3 +177,4 @@
 test_single_value_inheritance()
 test_artifact_path_requirements()
 test_prefixed_sort_order()
+test_inherits_in_regular_variables()
diff --git a/tools/atree/fs.cpp b/tools/atree/fs.cpp
index 6cd080e..d004e97 100644
--- a/tools/atree/fs.cpp
+++ b/tools/atree/fs.cpp
@@ -177,7 +177,7 @@
         } else {
             // Split the arguments if more than 1
             char* cmd = strdup(strip_cmd);
-            const char** args = (const char**) malloc(sizeof(const char*) * (num_args + 2));
+            const char** args = (const char**) calloc((num_args + 2), sizeof(const char*));
 
             const char** curr = args;
             char* s = cmd;
diff --git a/tools/compliance/cmd/checkshare/checkshare_test.go b/tools/compliance/cmd/checkshare/checkshare_test.go
index fdcab29..079691c 100644
--- a/tools/compliance/cmd/checkshare/checkshare_test.go
+++ b/tools/compliance/cmd/checkshare/checkshare_test.go
@@ -241,6 +241,59 @@
 			roots:          []string{"lib/libd.so.meta_lic"},
 			expectedStdout: "PASS",
 		},
+		{
+			condition:      "regressconcur",
+			name:           "container",
+			roots:          []string{"container.zip.meta_lic"},
+			expectedStdout: "FAIL",
+			expectedOutcomes: outcomeList{
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin1.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin2.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin3.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin4.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin5.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin6.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin7.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin8.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+				&outcome{
+					target:           "testdata/regressconcur/bin/bin9.meta_lic",
+					privacyCondition: "proprietary",
+					shareCondition:   "restricted",
+				},
+			},
+		},
 	}
 	for _, tt := range tests {
 		t.Run(tt.condition+" "+tt.name, func(t *testing.T) {
diff --git a/tools/compliance/cmd/testdata/regressconcur/README.md b/tools/compliance/cmd/testdata/regressconcur/README.md
new file mode 100644
index 0000000..98ab0ef
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/README.md
@@ -0,0 +1,62 @@
+## Start long walks followed by short walks
+
+Detect concurrency error where "already started" treated as
+"already finished".
+
+### Testdata build graph structure:
+
+A restricted licensed library sandwiched between a notice library and a notice
+binary. The source-code for the libraries only needs to be shared if shipped
+alongside the container with the binaries.
+
+```dot
+strict digraph {
+	rankdir=LR;
+	bin1 [label="bin/bin1.meta_lic\nproprietary"];
+	bin2 [label="bin/bin2.meta_lic\nproprietary"];
+	bin3 [label="bin/bin3.meta_lic\nproprietary"];
+	bin4 [label="bin/bin4.meta_lic\nproprietary"];
+	bin5 [label="bin/bin5.meta_lic\nproprietary"];
+	bin6 [label="bin/bin6.meta_lic\nproprietary"];
+	bin7 [label="bin/bin7.meta_lic\nproprietary"];
+	bin8 [label="bin/bin8.meta_lic\nproprietary"];
+	bin9 [label="bin/bin9.meta_lic\nproprietary"];
+	container [label="container.zip.meta_lic\nnotice"];
+	lib1 [label="lib/lib1.so.meta_lic\nnotice"];
+	lib2 [label="lib/lib2.so.meta_lic\nnotice"];
+	lib3 [label="lib/lib3.so.meta_lic\nnotice"];
+	lib4 [label="lib/lib4.so.meta_lic\nnotice"];
+	lib5 [label="lib/lib5.so.meta_lic\nnotice"];
+	lib6 [label="lib/lib6.so.meta_lic\nnotice"];
+	lib7 [label="lib/lib7.so.meta_lic\nnotice"];
+	lib8 [label="lib/lib8.so.meta_lic\nnotice"];
+	lib9 [label="lib/lib9.so.meta_lic\nrestricted"];
+	container -> bin1 [label="static"];
+	container -> bin2 [label="static"];
+	container -> bin3 [label="static"];
+	container -> bin4 [label="static"];
+	container -> bin5 [label="static"];
+	container -> bin6 [label="static"];
+	container -> bin7 [label="static"];
+	container -> bin8 [label="static"];
+	container -> bin9 [label="static"];
+	bin1 -> lib1 [label="static"];
+	bin2 -> lib2 [label="static"];
+	bin3 -> lib3 [label="static"];
+	bin4 -> lib4 [label="static"];
+	bin5 -> lib5 [label="static"];
+	bin6 -> lib6 [label="static"];
+	bin7 -> lib7 [label="static"];
+	bin8 -> lib8 [label="static"];
+	bin9 -> lib9 [label="static"];
+	lib1 -> lib2 [label="static"];
+	lib2 -> lib3 [label="static"];
+	lib3 -> lib4 [label="static"];
+	lib4 -> lib5 [label="static"];
+	lib5 -> lib6 [label="static"];
+	lib6 -> lib7 [label="static"];
+	lib7 -> lib8 [label="static"];
+	lib8 -> lib9 [label="static"];
+	{rank=same; container}
+}
+```
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin1.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin1.meta_lic
new file mode 100644
index 0000000..e3763f6
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin1.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin1"
+installed:  "out/target/product/fictional/system/bin/bin1"
+sources:  "out/target/product/fictional/system/lib/lib1.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib1.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin2.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin2.meta_lic
new file mode 100644
index 0000000..e1822bb
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin2.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin2"
+installed:  "out/target/product/fictional/system/bin/bin2"
+sources:  "out/target/product/fictional/system/lib/lib2.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib2.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin3.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin3.meta_lic
new file mode 100644
index 0000000..35f5d74
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin3.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin3"
+installed:  "out/target/product/fictional/system/bin/bin3"
+sources:  "out/target/product/fictional/system/lib/lib3.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib3.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin4.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin4.meta_lic
new file mode 100644
index 0000000..3287382
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin4.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin4"
+installed:  "out/target/product/fictional/system/bin/bin4"
+sources:  "out/target/product/fictional/system/lib/lib4.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib4.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin5.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin5.meta_lic
new file mode 100644
index 0000000..f51bcdb
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin5.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin5"
+installed:  "out/target/product/fictional/system/bin/bin5"
+sources:  "out/target/product/fictional/system/lib/lib5.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib5.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin6.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin6.meta_lic
new file mode 100644
index 0000000..4c99b01
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin6.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin6"
+installed:  "out/target/product/fictional/system/bin/bin6"
+sources:  "out/target/product/fictional/system/lib/lib6.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib6.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin7.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin7.meta_lic
new file mode 100644
index 0000000..565a338
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin7.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin7"
+installed:  "out/target/product/fictional/system/bin/bin7"
+sources:  "out/target/product/fictional/system/lib/lib7.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib7.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin8.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin8.meta_lic
new file mode 100644
index 0000000..f66c2c9
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin8.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin8"
+installed:  "out/target/product/fictional/system/bin/bin8"
+sources:  "out/target/product/fictional/system/lib/lib8.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib8.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/bin/bin9.meta_lic b/tools/compliance/cmd/testdata/regressconcur/bin/bin9.meta_lic
new file mode 100644
index 0000000..0aac4c6
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/bin/bin9.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+module_classes: "EXECUTABLES"
+projects:  "bin/onelibrary"
+license_kinds:  "legacy_proprietary"
+license_conditions:  "proprietary"
+is_container:  false
+built:  "out/target/product/fictional/obj/EXECUTABLES/bin_intermediates/bin9"
+installed:  "out/target/product/fictional/system/bin/bin9"
+sources:  "out/target/product/fictional/system/lib/lib9.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib9.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/container.zip.meta_lic b/tools/compliance/cmd/testdata/regressconcur/container.zip.meta_lic
new file mode 100644
index 0000000..88683d4
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/container.zip.meta_lic
@@ -0,0 +1,60 @@
+package_name:  "Android"
+projects:  "container/zip"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  true
+built:  "out/target/product/fictional/obj/ETC/container_intermediates/container.zip"
+installed:  "out/target/product/fictional/data/container.zip"
+install_map {
+  from_path:  "out/target/product/fictional/system/lib/"
+  container_path:  "/"
+}
+install_map {
+  from_path:  "out/target/product/fictional/system/bin/"
+  container_path:  "/"
+}
+sources:  "out/target/product/fictional/system/bin/bin1"
+sources:  "out/target/product/fictional/system/bin/bin2"
+sources:  "out/target/product/fictional/system/bin/bin3"
+sources:  "out/target/product/fictional/system/bin/bin4"
+sources:  "out/target/product/fictional/system/bin/bin5"
+sources:  "out/target/product/fictional/system/bin/bin6"
+sources:  "out/target/product/fictional/system/bin/bin7"
+sources:  "out/target/product/fictional/system/bin/bin8"
+sources:  "out/target/product/fictional/system/bin/bin9"
+deps:  {
+  file:  "testdata/regressconcur/bin/bin1.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin2.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin3.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin4.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin5.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin6.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin7.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin8.meta_lic"
+  annotations:  "static"
+}
+deps:  {
+  file:  "testdata/regressconcur/bin/bin9.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib1.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib1.a.meta_lic
new file mode 100644
index 0000000..89ebd7c
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib1.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib1.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib1.a"
+installed:  "out/target/product/fictional/system/lib/lib1.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib2.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib2.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib2.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib2.a.meta_lic
new file mode 100644
index 0000000..ec84287
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib2.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib2.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib2.a"
+installed:  "out/target/product/fictional/system/lib/lib2.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib3.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib3.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib3.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib3.a.meta_lic
new file mode 100644
index 0000000..1949c06
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib3.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib3.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib3.a"
+installed:  "out/target/product/fictional/system/lib/lib3.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib4.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib4.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib4.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib4.a.meta_lic
new file mode 100644
index 0000000..4dc777b
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib4.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib4.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib4.a"
+installed:  "out/target/product/fictional/system/lib/lib4.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib5.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib5.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib5.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib5.a.meta_lic
new file mode 100644
index 0000000..5d005dc
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib5.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib5.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib5.a"
+installed:  "out/target/product/fictional/system/lib/lib5.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib6.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib6.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib6.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib6.a.meta_lic
new file mode 100644
index 0000000..f2920c3
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib6.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib6.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib6.a"
+installed:  "out/target/product/fictional/system/lib/lib6.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib7.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib7.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib7.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib7.a.meta_lic
new file mode 100644
index 0000000..28c0c5f
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib7.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib7.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib7.a"
+installed:  "out/target/product/fictional/system/lib/lib7.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib8.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib8.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib8.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib8.a.meta_lic
new file mode 100644
index 0000000..b887edc
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib8.a.meta_lic
@@ -0,0 +1,13 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-MIT"
+license_conditions:  "notice"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib8.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib8.a"
+installed:  "out/target/product/fictional/system/lib/lib8.so"
+sources:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib9.a"
+deps:  {
+  file:  "testdata/regressconcur/lib/lib9.a.meta_lic"
+  annotations:  "static"
+}
diff --git a/tools/compliance/cmd/testdata/regressconcur/lib/lib9.a.meta_lic b/tools/compliance/cmd/testdata/regressconcur/lib/lib9.a.meta_lic
new file mode 100644
index 0000000..9bf155f
--- /dev/null
+++ b/tools/compliance/cmd/testdata/regressconcur/lib/lib9.a.meta_lic
@@ -0,0 +1,8 @@
+package_name:  "Android"
+projects:  "lib/restricted"
+license_kinds:  "SPDX-license-identifier-GPL-2.0"
+license_conditions:  "restricted"
+is_container:  false
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib9.so"
+built:  "out/target/product/fictional/obj/SHARED_LIBRARIES/lib_intermediates/lib9.a"
+installed:  "out/target/product/fictional/system/lib/lib9.so"
diff --git a/tools/compliance/graph.go b/tools/compliance/graph.go
index 80a2f47..fac1d05 100644
--- a/tools/compliance/graph.go
+++ b/tools/compliance/graph.go
@@ -459,36 +459,25 @@
 }
 
 // TargetNodeSet describes a set of distinct nodes in a license graph.
-type TargetNodeSet struct {
-	nodes map[*TargetNode]struct{}
-}
+type TargetNodeSet map[*TargetNode]struct{}
 
 // Contains returns true when `target` is an element of the set.
-func (ts *TargetNodeSet) Contains(target *TargetNode) bool {
-	_, isPresent := ts.nodes[target]
+func (ts TargetNodeSet) Contains(target *TargetNode) bool {
+	_, isPresent := ts[target]
 	return isPresent
 }
 
-// AsList returns the list of target nodes in the set. (unordered)
-func (ts *TargetNodeSet) AsList() TargetNodeList {
-	result := make(TargetNodeList, 0, len(ts.nodes))
-	for tn := range ts.nodes {
-		result = append(result, tn)
-	}
-	return result
-}
-
 // Names returns the array of target node namess in the set. (unordered)
-func (ts *TargetNodeSet) Names() []string {
-	result := make([]string, 0, len(ts.nodes))
-	for tn := range ts.nodes {
+func (ts TargetNodeSet) Names() []string {
+	result := make([]string, 0, len(ts))
+	for tn := range ts {
 		result = append(result, tn.name)
 	}
 	return result
 }
 
 // String returns a human-readable string representation of the set.
-func (ts *TargetNodeSet) String() string {
+func (ts TargetNodeSet) String() string {
 	return fmt.Sprintf("{%s}", strings.Join(ts.Names(), ", "))
 }
 
diff --git a/tools/compliance/noticeindex.go b/tools/compliance/noticeindex.go
index dbfede6..c91a8df 100644
--- a/tools/compliance/noticeindex.go
+++ b/tools/compliance/noticeindex.go
@@ -42,7 +42,7 @@
 	// rs identifies the set of resolutions upon which the index is based.
 	rs ResolutionSet
 	// shipped identifies the set of target nodes shipped directly or as derivative works.
-	shipped *TargetNodeSet
+	shipped TargetNodeSet
 	// rootFS locates the root of the file system from which to read the files.
 	rootFS fs.FS
 	// hash maps license text filenames to content hashes
diff --git a/tools/compliance/policy_policy.go b/tools/compliance/policy_policy.go
index 23e25c6..368a162 100644
--- a/tools/compliance/policy_policy.go
+++ b/tools/compliance/policy_policy.go
@@ -114,7 +114,7 @@
 
 // LicenseConditionSetFromNames returns a set containing the recognized `names` and
 // silently ignoring or discarding the unrecognized `names`.
-func LicenseConditionSetFromNames(tn *TargetNode, names ...string) LicenseConditionSet {
+func LicenseConditionSetFromNames(names ...string) LicenseConditionSet {
 	cs := NewLicenseConditionSet()
 	for _, name := range names {
 		if lc, ok := RecognizedConditionNames[name]; ok {
diff --git a/tools/compliance/policy_resolve.go b/tools/compliance/policy_resolve.go
index fc8ed4c..0951ba1 100644
--- a/tools/compliance/policy_resolve.go
+++ b/tools/compliance/policy_resolve.go
@@ -14,10 +14,6 @@
 
 package compliance
 
-import (
-	"sync"
-)
-
 var (
 	// AllResolutions is a TraceConditions function that resolves all
 	// unfiltered license conditions.
@@ -53,16 +49,10 @@
 		// amap identifes targets previously walked. (guarded by mu)
 		amap := make(map[*TargetNode]struct{})
 
-		// mu guards concurrent access to amap
-		var mu sync.Mutex
-
 		var walk func(target *TargetNode, treatAsAggregate bool) LicenseConditionSet
 
 		walk = func(target *TargetNode, treatAsAggregate bool) LicenseConditionSet {
 			priorWalkResults := func() (LicenseConditionSet, bool) {
-				mu.Lock()
-				defer mu.Unlock()
-
 				if _, alreadyWalked := amap[target]; alreadyWalked {
 					if treatAsAggregate {
 						return target.resolution, true
@@ -84,25 +74,17 @@
 				return cs
 			}
 
-			c := make(chan LicenseConditionSet, len(target.edges))
 			// add all the conditions from all the dependencies
 			for _, edge := range target.edges {
-				go func(edge *TargetEdge) {
-					// walk dependency to get its conditions
-					cs := walk(edge.dependency, treatAsAggregate && edge.dependency.IsContainer())
+				// walk dependency to get its conditions
+				dcs := walk(edge.dependency, treatAsAggregate && edge.dependency.IsContainer())
 
-					// turn those into the conditions that apply to the target
-					cs = depConditionsPropagatingToTarget(lg, edge, cs, treatAsAggregate)
-
-					c <- cs
-				}(edge)
+				// turn those into the conditions that apply to the target
+				dcs = depConditionsPropagatingToTarget(lg, edge, dcs, treatAsAggregate)
+				cs |= dcs
 			}
-			for i := 0; i < len(target.edges); i++ {
-				cs |= <-c
-			}
-			mu.Lock()
 			target.resolution |= cs
-			mu.Unlock()
+			cs = target.resolution
 
 			// return conditions up the tree
 			return cs
@@ -133,33 +115,21 @@
 
 	// short-cut if already walked and cached
 	lg.onceTopDown.Do(func() {
-		wg := &sync.WaitGroup{}
-		wg.Add(1)
-
 		// start with the conditions propagated up the graph
 		TraceBottomUpConditions(lg, conditionsFn)
 
 		// amap contains the set of targets already walked. (guarded by mu)
 		amap := make(map[*TargetNode]struct{})
 
-		// mu guards concurrent access to amap
-		var mu sync.Mutex
-
 		var walk func(fnode *TargetNode, cs LicenseConditionSet, treatAsAggregate bool)
 
 		walk = func(fnode *TargetNode, cs LicenseConditionSet, treatAsAggregate bool) {
-			defer wg.Done()
 			continueWalk := func() bool {
-				mu.Lock()
-				defer mu.Unlock()
-
-				depcs := fnode.resolution
-				_, alreadyWalked := amap[fnode]
-				if alreadyWalked {
+				if _, alreadyWalked := amap[fnode]; alreadyWalked {
 					if cs.IsEmpty() {
 						return false
 					}
-					if cs.Difference(depcs).IsEmpty() {
+					if cs.Difference(fnode.resolution).IsEmpty() {
 						// no new conditions
 
 						// pure aggregates never need walking a 2nd time with same conditions
@@ -172,8 +142,9 @@
 						}
 						// previously walked as pure aggregate; need to re-walk as non-aggregate
 					}
+				} else {
+					fnode.resolution |= conditionsFn(fnode)
 				}
-				fnode.resolution |= conditionsFn(fnode)
 				fnode.resolution |= cs
 				fnode.pure = treatAsAggregate
 				amap[fnode] = struct{}{}
@@ -189,19 +160,15 @@
 				dcs := targetConditionsPropagatingToDep(lg, edge, cs, treatAsAggregate, conditionsFn)
 				dnode := edge.dependency
 				// add the conditions to the dependency
-				wg.Add(1)
-				go walk(dnode, dcs, treatAsAggregate && dnode.IsContainer())
+				walk(dnode, dcs, treatAsAggregate && dnode.IsContainer())
 			}
 		}
 
 		// walk each of the roots
 		for _, rname := range lg.rootFiles {
 			rnode := lg.targets[rname]
-			wg.Add(1)
 			// add the conditions to the root and its transitive closure
-			go walk(rnode, NewLicenseConditionSet(), rnode.IsContainer())
+			walk(rnode, NewLicenseConditionSet(), rnode.IsContainer())
 		}
-		wg.Done()
-		wg.Wait()
 	})
 }
diff --git a/tools/compliance/policy_resolvenotices_test.go b/tools/compliance/policy_resolvenotices_test.go
index b62d62f..b23e587 100644
--- a/tools/compliance/policy_resolvenotices_test.go
+++ b/tools/compliance/policy_resolvenotices_test.go
@@ -33,8 +33,8 @@
 				{"apacheBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -44,7 +44,7 @@
 				{"apacheBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -54,8 +54,8 @@
 				{"apacheBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -66,11 +66,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -81,8 +79,8 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -96,22 +94,17 @@
 				{"mitBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "mplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "mplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
-				{"mitBin.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mitBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "mitBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "mplLib.meta_lic", "reciprocal|restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "mplLib.meta_lic", "reciprocal|restricted"},
+				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
+				{"mitBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -122,12 +115,11 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -138,8 +130,8 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -150,11 +142,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"mitLib.meta_lic", "mitLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"mitLib.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "restricted"},
+				{"mitLib.meta_lic", "mitLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -168,14 +158,11 @@
 				{"mitBin.meta_lic", "mitLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"mitBin.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "mitBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -186,10 +173,9 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -200,12 +186,11 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -216,11 +201,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice|restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -231,8 +214,8 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -243,9 +226,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -257,18 +240,13 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheContainer.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheContainer.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "mitLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "mitLib.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice|restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -279,12 +257,11 @@
 				{"apacheContainer.meta_lic", "lgplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"lgplLib.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -295,8 +272,8 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -307,9 +284,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"lgplLib.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
+				{"lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -320,9 +297,9 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -333,10 +310,10 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"lgplLib.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -347,9 +324,9 @@
 				{"apacheContainer.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -360,10 +337,10 @@
 				{"apacheContainer.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"lgplLib.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"lgplLib.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -374,9 +351,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -387,9 +364,9 @@
 				{"dependentModule.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"dependentModule.meta_lic", "dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
-				{"dependentModule.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
-				{"dependentModule.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"dependentModule.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -400,8 +377,8 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -412,9 +389,9 @@
 				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "mitLib.meta_lic", "notice"},
+				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -425,8 +402,8 @@
 				{"dependentModule.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"dependentModule.meta_lic", "dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
-				{"dependentModule.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -437,9 +414,9 @@
 				{"dependentModule.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"dependentModule.meta_lic", "dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
-				{"dependentModule.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "mitLib.meta_lic", "notice"},
+				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 	}
diff --git a/tools/compliance/policy_resolveprivacy_test.go b/tools/compliance/policy_resolveprivacy_test.go
index e8c953a..d4d1967 100644
--- a/tools/compliance/policy_resolveprivacy_test.go
+++ b/tools/compliance/policy_resolveprivacy_test.go
@@ -57,7 +57,7 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
 			},
 		},
 		{
@@ -67,7 +67,7 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"gplBin.meta_lic", "proprietary.meta_lic", "proprietary"},
 			},
 		},
 	}
diff --git a/tools/compliance/policy_resolveshare_test.go b/tools/compliance/policy_resolveshare_test.go
index faade88..4abd960 100644
--- a/tools/compliance/policy_resolveshare_test.go
+++ b/tools/compliance/policy_resolveshare_test.go
@@ -73,8 +73,8 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
-				{"lgplBin.meta_lic", "apacheLib.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "apacheLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -84,7 +84,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -94,7 +94,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -104,8 +104,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -115,9 +115,9 @@
 				{"gplContainer.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplContainer.meta_lic", "gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"gplContainer.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "apacheLib.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -128,9 +128,9 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -141,9 +141,9 @@
 				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -153,7 +153,7 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -163,9 +163,9 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "apacheLib.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -207,8 +207,8 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "proprietary.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -218,8 +218,8 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "proprietary.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "proprietary.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -245,7 +245,7 @@
 				{"mitBin.meta_lic", "mplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
+				{"mitBin.meta_lic", "mplLib.meta_lic", "reciprocal"},
 			},
 		},
 		{
@@ -255,7 +255,7 @@
 				{"mplBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mplBin.meta_lic", "mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
+				{"mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
 			},
 		},
 	}
diff --git a/tools/compliance/policy_shipped.go b/tools/compliance/policy_shipped.go
index 75c8399..b21a95a 100644
--- a/tools/compliance/policy_shipped.go
+++ b/tools/compliance/policy_shipped.go
@@ -16,15 +16,15 @@
 
 // ShippedNodes returns the set of nodes in a license graph where the target or
 // a derivative work gets distributed. (caches result)
-func ShippedNodes(lg *LicenseGraph) *TargetNodeSet {
+func ShippedNodes(lg *LicenseGraph) TargetNodeSet {
 	lg.mu.Lock()
 	shipped := lg.shippedNodes
 	lg.mu.Unlock()
 	if shipped != nil {
-		return shipped
+		return *shipped
 	}
 
-	tset := make(map[*TargetNode]struct{})
+	tset := make(TargetNodeSet)
 
 	WalkTopDown(NoEdgeContext{}, lg, func(lg *LicenseGraph, tn *TargetNode, path TargetEdgePath) bool {
 		if _, alreadyWalked := tset[tn]; alreadyWalked {
@@ -39,7 +39,7 @@
 		return true
 	})
 
-	shipped = &TargetNodeSet{tset}
+	shipped = &tset
 
 	lg.mu.Lock()
 	if lg.shippedNodes == nil {
@@ -50,5 +50,5 @@
 	}
 	lg.mu.Unlock()
 
-	return shipped
+	return *shipped
 }
diff --git a/tools/compliance/policy_walk.go b/tools/compliance/policy_walk.go
index beb6d53..e6b94ab 100644
--- a/tools/compliance/policy_walk.go
+++ b/tools/compliance/policy_walk.go
@@ -247,40 +247,16 @@
 // WalkActionsForCondition performs a top-down walk of the LicenseGraph
 // resolving all distributed works for `conditions`.
 func WalkActionsForCondition(lg *LicenseGraph, conditions LicenseConditionSet) ActionSet {
-	shipped := ShippedNodes(lg)
-
-	// cmap identifies previously walked target/condition pairs.
-	cmap := make(map[resolutionKey]struct{})
-
 	// amap maps 'actsOn' targets to the applicable conditions
 	//
 	// amap is the resulting ActionSet
 	amap := make(ActionSet)
-	WalkTopDown(ApplicableConditionsContext{conditions}, lg, func(lg *LicenseGraph, tn *TargetNode, path TargetEdgePath) bool {
-		universe := conditions
-		if len(path) > 0 {
-			universe = path[len(path)-1].ctx.(LicenseConditionSet)
+
+	for tn := range ShippedNodes(lg) {
+		if cs := conditions.Intersection(tn.resolution); !cs.IsEmpty() {
+			amap[tn] = cs
 		}
-		if universe.IsEmpty() {
-			return false
-		}
-		key := resolutionKey{tn, universe}
-		if _, ok := cmap[key]; ok {
-			return false
-		}
-		if !shipped.Contains(tn) {
-			return false
-		}
-		cs := universe.Intersection(tn.resolution)
-		if !cs.IsEmpty() {
-			if _, ok := amap[tn]; ok {
-				amap[tn] = cs
-			} else {
-				amap[tn] = amap[tn].Union(cs)
-			}
-		}
-		return true
-	})
+	}
 
 	return amap
 }
diff --git a/tools/compliance/policy_walk_test.go b/tools/compliance/policy_walk_test.go
index 0bc37f8..53af3be 100644
--- a/tools/compliance/policy_walk_test.go
+++ b/tools/compliance/policy_walk_test.go
@@ -48,8 +48,8 @@
 				{"apacheBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -60,8 +60,8 @@
 				{"mitBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mitBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
+				{"mitBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -72,9 +72,8 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "lgplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "lgplLib.meta_lic", "lgplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted_if_statically_linked"},
+				{"apacheBin.meta_lic", "lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -85,7 +84,7 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -96,7 +95,7 @@
 				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -116,8 +115,8 @@
 				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -137,7 +136,7 @@
 				{"dependentModule.meta_lic", "gplWithClasspathException.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"dependentModule.meta_lic", "dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
 			},
 		},
 		{
@@ -157,9 +156,8 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
-				{"lgplBin.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"lgplBin.meta_lic", "apacheLib.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "apacheLib.meta_lic", "notice|restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -170,8 +168,8 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
-				{"lgplBin.meta_lic", "apacheLib.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplBin.meta_lic", "apacheLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -182,7 +180,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -193,7 +191,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -204,9 +202,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "apacheLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -217,8 +214,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -229,11 +226,9 @@
 				{"gplContainer.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplContainer.meta_lic", "gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"gplContainer.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"gplContainer.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "apacheLib.meta_lic", "notice|restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -244,9 +239,9 @@
 				{"gplContainer.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplContainer.meta_lic", "gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"gplContainer.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "apacheLib.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -258,12 +253,11 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheContainer.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -275,9 +269,9 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -289,11 +283,9 @@
 				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice|restricted"},
+				{"apacheBin.meta_lic", "apacheLib.meta_lic", "notice|restricted"},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -305,9 +297,9 @@
 				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "apacheLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheBin.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "apacheLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -318,7 +310,7 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -329,7 +321,7 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -340,9 +332,9 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "apacheLib.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -353,7 +345,7 @@
 				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -382,8 +374,8 @@
 				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
-				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -403,7 +395,7 @@
 				{"gplWithClasspathException.meta_lic", "dependentModule.meta_lic", []string{"dynamic"}},
 			},
 			expectedResolutions: []res{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -432,9 +424,8 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
-				{"proprietary.meta_lic", "proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "proprietary.meta_lic", "restricted|proprietary"},
+				{"proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -445,8 +436,8 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"proprietary.meta_lic", "gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "proprietary.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -457,7 +448,7 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
 			},
 		},
 		{
@@ -468,9 +459,8 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
-				{"gplBin.meta_lic", "proprietary.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "proprietary.meta_lic", "restricted|proprietary"},
 			},
 		},
 		{
@@ -481,8 +471,8 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"gplBin.meta_lic", "proprietary.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "proprietary.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -493,7 +483,7 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"gplBin.meta_lic", "proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"gplBin.meta_lic", "proprietary.meta_lic", "proprietary"},
 			},
 		},
 		{
@@ -504,8 +494,8 @@
 				{"mitBin.meta_lic", "by_exception.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mitBin.meta_lic", "by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
+				{"mitBin.meta_lic", "by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -525,7 +515,7 @@
 				{"mitBin.meta_lic", "by_exception.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"mitBin.meta_lic", "by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -536,8 +526,8 @@
 				{"by_exception.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
-				{"by_exception.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"by_exception.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -557,7 +547,7 @@
 				{"by_exception.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -568,8 +558,8 @@
 				{"mitBin.meta_lic", "mplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mitBin.meta_lic", "mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
+				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
+				{"mitBin.meta_lic", "mplLib.meta_lic", "reciprocal"},
 			},
 		},
 		{
@@ -580,7 +570,7 @@
 				{"mitBin.meta_lic", "mplLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mitBin.meta_lic", "mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
+				{"mitBin.meta_lic", "mplLib.meta_lic", "reciprocal"},
 			},
 		},
 		{
@@ -591,8 +581,8 @@
 				{"mplBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mplBin.meta_lic", "mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
-				{"mplBin.meta_lic", "mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
+				{"mplBin.meta_lic", "mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -603,7 +593,7 @@
 				{"mplBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedResolutions: []res{
-				{"mplBin.meta_lic", "mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
+				{"mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
 			},
 		},
 	}
@@ -639,8 +629,8 @@
 				{"apacheBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "notice"},
+				{"apacheLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -651,8 +641,8 @@
 				{"mitBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"mitBin.meta_lic", "notice"},
+				{"mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -663,9 +653,8 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "lgplLib.meta_lic", "restricted"},
-				{"lgplLib.meta_lic", "lgplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "notice"},
+				{"lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -676,7 +665,7 @@
 				{"apacheBin.meta_lic", "lgplLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -687,7 +676,7 @@
 				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -707,8 +696,8 @@
 				{"apacheBin.meta_lic", "gplWithClasspathException.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"apacheBin.meta_lic", "notice"},
+				{"gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -728,7 +717,7 @@
 				{"dependentModule.meta_lic", "gplWithClasspathException.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"dependentModule.meta_lic", "dependentModule.meta_lic", "notice"},
+				{"dependentModule.meta_lic", "notice"},
 			},
 		},
 		{
@@ -748,9 +737,8 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"apacheLib.meta_lic", "notice|restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -761,8 +749,8 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "restricted_if_statically_linked"},
+				{"apacheLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -773,7 +761,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -784,7 +772,7 @@
 				{"lgplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"lgplBin.meta_lic", "lgplBin.meta_lic", "restricted"},
+				{"lgplBin.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 		{
@@ -795,9 +783,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -808,8 +795,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -820,11 +807,8 @@
 				{"gplContainer.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "notice|restricted"},
 			},
 		},
 		{
@@ -835,9 +819,8 @@
 				{"gplContainer.meta_lic", "apacheLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplContainer.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "gplContainer.meta_lic", "restricted"},
+				{"gplContainer.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -849,11 +832,9 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheContainer.meta_lic", "apacheContainer.meta_lic", "notice"},
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "notice|restricted"},
+				{"apacheLib.meta_lic", "notice"},
+				{"gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -865,8 +846,8 @@
 				{"apacheContainer.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheContainer.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheContainer.meta_lic", "restricted"},
+				{"gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -878,11 +859,9 @@
 				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "apacheLib.meta_lic", "notice"},
-				{"apacheLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "notice|restricted"},
+				{"apacheLib.meta_lic", "notice|restricted"},
+				{"gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -894,9 +873,9 @@
 				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"apacheBin.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"apacheBin.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "restricted"},
+				{"gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -907,7 +886,7 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -918,7 +897,7 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -929,8 +908,8 @@
 				{"gplBin.meta_lic", "apacheLib.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"apacheLib.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
+				{"apacheLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -941,7 +920,7 @@
 				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -970,8 +949,8 @@
 				{"gplWithClasspathException.meta_lic", "apacheBin.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
-				{"apacheBin.meta_lic", "apacheBin.meta_lic", "notice"},
+				{"gplWithClasspathException.meta_lic", "permissive"},
+				{"apacheBin.meta_lic", "notice"},
 			},
 		},
 		{
@@ -991,7 +970,7 @@
 				{"gplWithClasspathException.meta_lic", "dependentModule.meta_lic", []string{"dynamic"}},
 			},
 			expectedActions: []act{
-				{"gplWithClasspathException.meta_lic", "gplWithClasspathException.meta_lic", "permissive"},
+				{"gplWithClasspathException.meta_lic", "permissive"},
 			},
 		},
 		{
@@ -1020,9 +999,8 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
-				{"proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "restricted|proprietary"},
+				{"gplLib.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -1033,8 +1011,8 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplLib.meta_lic", "gplLib.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "gplLib.meta_lic", "restricted"},
+				{"gplLib.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -1045,7 +1023,7 @@
 				{"proprietary.meta_lic", "gplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"proprietary.meta_lic", "proprietary"},
 			},
 		},
 		{
@@ -1056,9 +1034,8 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
-				{"proprietary.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "restricted|proprietary"},
 			},
 		},
 		{
@@ -1069,8 +1046,8 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"gplBin.meta_lic", "gplBin.meta_lic", "restricted"},
-				{"proprietary.meta_lic", "gplBin.meta_lic", "restricted"},
+				{"gplBin.meta_lic", "restricted"},
+				{"proprietary.meta_lic", "restricted"},
 			},
 		},
 		{
@@ -1081,7 +1058,7 @@
 				{"gplBin.meta_lic", "proprietary.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"proprietary.meta_lic", "proprietary.meta_lic", "proprietary"},
+				{"proprietary.meta_lic", "proprietary"},
 			},
 		},
 		{
@@ -1092,8 +1069,8 @@
 				{"mitBin.meta_lic", "by_exception.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"mitBin.meta_lic", "notice"},
+				{"by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -1113,7 +1090,7 @@
 				{"mitBin.meta_lic", "by_exception.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -1124,8 +1101,8 @@
 				{"by_exception.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
-				{"mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"by_exception.meta_lic", "by_exception_only"},
+				{"mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -1145,7 +1122,7 @@
 				{"by_exception.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"by_exception.meta_lic", "by_exception.meta_lic", "by_exception_only"},
+				{"by_exception.meta_lic", "by_exception_only"},
 			},
 		},
 		{
@@ -1156,8 +1133,8 @@
 				{"mitBin.meta_lic", "mplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mitBin.meta_lic", "mitBin.meta_lic", "notice"},
-				{"mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
+				{"mitBin.meta_lic", "notice"},
+				{"mplLib.meta_lic", "reciprocal"},
 			},
 		},
 		{
@@ -1168,7 +1145,7 @@
 				{"mitBin.meta_lic", "mplLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mplLib.meta_lic", "mplLib.meta_lic", "reciprocal"},
+				{"mplLib.meta_lic", "reciprocal"},
 			},
 		},
 		{
@@ -1179,8 +1156,8 @@
 				{"mplBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
-				{"mitLib.meta_lic", "mitLib.meta_lic", "notice"},
+				{"mplBin.meta_lic", "reciprocal"},
+				{"mitLib.meta_lic", "notice"},
 			},
 		},
 		{
@@ -1191,7 +1168,25 @@
 				{"mplBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
 			},
 			expectedActions: []act{
-				{"mplBin.meta_lic", "mplBin.meta_lic", "reciprocal"},
+				{"mplBin.meta_lic", "reciprocal"},
+			},
+		},
+		{
+			name:      "regress-walk-twice",
+			condition: ImpliesShared,
+			roots:     []string{"mitBin.meta_lic", "apacheBin.meta_lic", "gplLib.meta_lic"},
+			edges: []annotated{
+				{"apacheBin.meta_lic", "mitLib.meta_lic", []string{"dynamic"}},
+				{"apacheBin.meta_lic", "gplLib.meta_lic", []string{"dynamic"}},
+				{"mitBin.meta_lic", "mitLib.meta_lic", []string{"static"}},
+				{"mitBin.meta_lic", "lgplLib.meta_lic", []string{"static"}},
+			},
+			expectedActions: []act{
+				{"apacheBin.meta_lic", "restricted"},
+				{"mitLib.meta_lic", "restricted|restricted_if_statically_linked"},
+				{"gplLib.meta_lic", "restricted"},
+				{"mitBin.meta_lic", "restricted_if_statically_linked"},
+				{"lgplLib.meta_lic", "restricted_if_statically_linked"},
 			},
 		},
 	}
diff --git a/tools/compliance/readgraph.go b/tools/compliance/readgraph.go
index bf364e6..a413ebe 100644
--- a/tools/compliance/readgraph.go
+++ b/tools/compliance/readgraph.go
@@ -175,7 +175,7 @@
 		}
 		lg.edges = make(TargetEdgeList, 0, esize)
 		for _, tn := range lg.targets {
-			tn.licenseConditions = LicenseConditionSetFromNames(tn, tn.proto.LicenseConditions...)
+			tn.licenseConditions = LicenseConditionSetFromNames(tn.proto.LicenseConditions...)
 			err = addDependencies(lg, tn)
 			if err != nil {
 				return nil, fmt.Errorf("error indexing dependencies for %q: %w", tn.name, err)
diff --git a/tools/compliance/resolutionset_test.go b/tools/compliance/resolutionset_test.go
index 89cdfeb..efdff82 100644
--- a/tools/compliance/resolutionset_test.go
+++ b/tools/compliance/resolutionset_test.go
@@ -27,48 +27,44 @@
 	// binc represents a compiler or other toolchain binary used for
 	// building the other binaries.
 	bottomUp = []res{
-		{"image", "image", "image", "notice"},
-		{"image", "image", "bin2", "restricted"},
-		{"image", "bin1", "bin1", "reciprocal"},
-		{"image", "bin2", "bin2", "restricted"},
-		{"image", "lib1", "lib1", "notice"},
-		{"image", "lib2", "lib2", "notice"},
-		{"binc", "binc", "binc", "proprietary"},
-		{"bin1", "bin1", "bin1", "reciprocal"},
-		{"bin1", "lib1", "lib1", "notice"},
-		{"bin2", "bin2", "bin2", "restricted"},
-		{"bin2", "lib2", "lib2", "notice"},
-		{"lib1", "lib1", "lib1", "notice"},
-		{"lib2", "lib2", "lib2", "notice"},
+		{"image", "image", "notice|restricted"},
+		{"image", "bin1", "reciprocal"},
+		{"image", "bin2", "restricted"},
+		{"image", "lib1", "notice"},
+		{"image", "lib2", "notice"},
+		{"binc", "binc", "proprietary"},
+		{"bin1", "bin1", "reciprocal"},
+		{"bin1", "lib1", "notice"},
+		{"bin2", "bin2", "restricted"},
+		{"bin2", "lib2", "notice"},
+		{"lib1", "lib1", "notice"},
+		{"lib2", "lib2", "notice"},
 	}
 
 	// notice describes bottomUp after a top-down notice resolve.
 	notice = []res{
-		{"image", "image", "image", "notice"},
-		{"image", "image", "bin2", "restricted"},
-		{"image", "bin1", "bin1", "reciprocal"},
-		{"image", "bin2", "bin2", "restricted"},
-		{"image", "lib1", "lib1", "notice"},
-		{"image", "lib2", "bin2", "restricted"},
-		{"image", "lib2", "lib2", "notice"},
-		{"bin1", "bin1", "bin1", "reciprocal"},
-		{"bin1", "lib1", "lib1", "notice"},
-		{"bin2", "bin2", "bin2", "restricted"},
-		{"bin2", "lib2", "bin2", "restricted"},
-		{"bin2", "lib2", "lib2", "notice"},
-		{"lib1", "lib1", "lib1", "notice"},
-		{"lib2", "lib2", "lib2", "notice"},
+		{"image", "image", "notice|restricted"},
+		{"image", "bin1", "reciprocal"},
+		{"image", "bin2", "restricted"},
+		{"image", "lib1", "notice"},
+		{"image", "lib2", "notice|restricted"},
+		{"bin1", "bin1", "reciprocal"},
+		{"bin1", "lib1", "notice"},
+		{"bin2", "bin2", "restricted"},
+		{"bin2", "lib2", "notice|restricted"},
+		{"lib1", "lib1", "notice"},
+		{"lib2", "lib2", "notice"},
 	}
 
 	// share describes bottomUp after a top-down share resolve.
 	share = []res{
-		{"image", "image", "bin2", "restricted"},
-		{"image", "bin1", "bin1", "reciprocal"},
-		{"image", "bin2", "bin2", "restricted"},
-		{"image", "lib2", "bin2", "restricted"},
-		{"bin1", "bin1", "bin1", "reciprocal"},
-		{"bin2", "bin2", "bin2", "restricted"},
-		{"bin2", "lib2", "bin2", "restricted"},
+		{"image", "image", "restricted"},
+		{"image", "bin1", "reciprocal"},
+		{"image", "bin2", "restricted"},
+		{"image", "lib2", "restricted"},
+		{"bin1", "bin1", "reciprocal"},
+		{"bin2", "bin2", "restricted"},
+		{"bin2", "lib2", "restricted"},
 	}
 
 	// proprietary describes bottomUp after a top-down proprietary resolve.
diff --git a/tools/compliance/test_util.go b/tools/compliance/test_util.go
index f0242e2..053b398 100644
--- a/tools/compliance/test_util.go
+++ b/tools/compliance/test_util.go
@@ -121,28 +121,24 @@
 	return tn
 }
 
-// newTestCondition constructs a test license condition in the license graph.
-func newTestCondition(lg *LicenseGraph, targetName string, conditionName string) LicenseCondition {
-	tn := newTestNode(lg, targetName)
-	cl := LicenseConditionSetFromNames(tn, conditionName).AsList()
+// newTestCondition constructs a test license condition.
+func newTestCondition(conditionName string) LicenseCondition {
+	cl := LicenseConditionSetFromNames(conditionName).AsList()
 	if len(cl) == 0 {
 		panic(fmt.Errorf("attempt to create unrecognized condition: %q", conditionName))
 	} else if len(cl) != 1 {
 		panic(fmt.Errorf("unexpected multiple conditions from condition name: %q: got %d, want 1", conditionName, len(cl)))
 	}
 	lc := cl[0]
-	tn.licenseConditions = tn.licenseConditions.Plus(lc)
 	return lc
 }
 
-// newTestConditionSet constructs a test license condition set in the license graph.
-func newTestConditionSet(lg *LicenseGraph, targetName string, conditionName []string) LicenseConditionSet {
-	tn := newTestNode(lg, targetName)
-	cs := LicenseConditionSetFromNames(tn, conditionName...)
+// newTestConditionSet constructs a test license condition set.
+func newTestConditionSet(conditionName []string) LicenseConditionSet {
+	cs := LicenseConditionSetFromNames(conditionName...)
 	if cs.IsEmpty() {
 		panic(fmt.Errorf("attempt to create unrecognized condition: %q", conditionName))
 	}
-	tn.licenseConditions = tn.licenseConditions.Union(cs)
 	return cs
 }
 
@@ -283,12 +279,12 @@
 
 // act describes test data resolution actions to define test action sets.
 type act struct {
-	actsOn, origin, condition string
+	actsOn, condition string
 }
 
 // String returns a human-readable string representing the test action.
 func (a act) String() string {
-	return fmt.Sprintf("%s{%s:%s}", a.actsOn, a.origin, a.condition)
+	return fmt.Sprintf("%s{%s}", a.actsOn, a.condition)
 }
 
 // toActionSet converts a list of act test data into a test action set.
@@ -296,7 +292,7 @@
 	as := make(ActionSet)
 	for _, a := range data {
 		actsOn := newTestNode(lg, a.actsOn)
-		cs := newTestConditionSet(lg, a.origin, strings.Split(a.condition, "|"))
+		cs := newTestConditionSet(strings.Split(a.condition, "|"))
 		as[actsOn] = cs
 	}
 	return as
@@ -304,7 +300,7 @@
 
 // res describes test data resolutions to define test resolution sets.
 type res struct {
-	attachesTo, actsOn, origin, condition string
+	attachesTo, actsOn, condition string
 }
 
 // toResolutionSet converts a list of res test data into a test resolution set.
@@ -316,7 +312,7 @@
 		if _, ok := rmap[attachesTo]; !ok {
 			rmap[attachesTo] = make(ActionSet)
 		}
-		cs := newTestConditionSet(lg, r.origin, strings.Split(r.condition, ":"))
+		cs := newTestConditionSet(strings.Split(r.condition, "|"))
 		rmap[attachesTo][actsOn] |= cs
 	}
 	return rmap
@@ -416,15 +412,13 @@
 	result := make([]SourceSharePrivacyConflict, 0, len(data))
 	for _, c := range data {
 		fields := strings.Split(c.share, ":")
-		oshare := fields[0]
 		cshare := fields[1]
 		fields = strings.Split(c.privacy, ":")
-		oprivacy := fields[0]
 		cprivacy := fields[1]
 		result = append(result, SourceSharePrivacyConflict{
 			newTestNode(lg, c.sourceNode),
-			newTestCondition(lg, oshare, cshare),
-			newTestCondition(lg, oprivacy, cprivacy),
+			newTestCondition(cshare),
+			newTestCondition(cprivacy),
 		})
 	}
 	return result
diff --git a/tools/releasetools/sign_target_files_apks.py b/tools/releasetools/sign_target_files_apks.py
index 5f48dd0..0dd0790 100755
--- a/tools/releasetools/sign_target_files_apks.py
+++ b/tools/releasetools/sign_target_files_apks.py
@@ -531,7 +531,12 @@
       # RECOVERY/RAMDISK/default.prop is a legacy path, but will always exist
       # as a symlink in the current code. So it's a no-op here. Keeping the
       # path here for clarity.
-      "RECOVERY/RAMDISK/default.prop") or filename.endswith("build.prop")
+      # Some build props might be stored under path
+      # VENDOR_BOOT/RAMDISK_FRAGMENTS/recovery/RAMDISK/default.prop
+      # so overwrite all files that ends with build.prop or default.prop
+      "RECOVERY/RAMDISK/default.prop") or \
+        filename.endswith("build.prop") or \
+        filename.endswith("/default.prop")
 
 
 def ProcessTargetFiles(input_tf_zip, output_tf_zip, misc_info,
diff --git a/tools/warn/tidy_warn_patterns.py b/tools/warn/tidy_warn_patterns.py
index c138f1c..5ee66c0 100644
--- a/tools/warn/tidy_warn_patterns.py
+++ b/tools/warn/tidy_warn_patterns.py
@@ -224,6 +224,7 @@
     analyzer_warn_check('clang-analyzer-valist.Unterminated'),
     analyzer_group_check('clang-analyzer-core.uninitialized'),
     analyzer_group_check('clang-analyzer-deadcode'),
+    analyzer_warn_check('clang-analyzer-security.insecureAPI.DeprecatedOrUnsafeBufferHandling'),
     analyzer_warn_check('clang-analyzer-security.insecureAPI.bcmp'),
     analyzer_warn_check('clang-analyzer-security.insecureAPI.bcopy'),
     analyzer_warn_check('clang-analyzer-security.insecureAPI.bzero'),
diff --git a/tools/zipalign/ZipEntry.cpp b/tools/zipalign/ZipEntry.cpp
index fcad96c..689999e 100644
--- a/tools/zipalign/ZipEntry.cpp
+++ b/tools/zipalign/ZipEntry.cpp
@@ -40,14 +40,10 @@
  */
 status_t ZipEntry::initFromCDE(FILE* fp)
 {
-    status_t result;
-    long posn; // NOLINT(google-runtime-int), for ftell/fseek
-    bool hasDD;
-
     //ALOGV("initFromCDE ---\n");
 
     /* read the CDE */
-    result = mCDE.read(fp);
+    status_t result = mCDE.read(fp);
     if (result != OK) {
         ALOGD("mCDE.read failed\n");
         return result;
@@ -56,8 +52,8 @@
     //mCDE.dump();
 
     /* using the info in the CDE, go load up the LFH */
-    posn = ftell(fp);
-    if (fseek(fp, mCDE.mLocalHeaderRelOffset, SEEK_SET) != 0) {
+    off_t posn = ftello(fp);
+    if (fseeko(fp, mCDE.mLocalHeaderRelOffset, SEEK_SET) != 0) {
         ALOGD("local header seek failed (%" PRIu32 ")\n",
             mCDE.mLocalHeaderRelOffset);
         return UNKNOWN_ERROR;
@@ -69,7 +65,7 @@
         return result;
     }
 
-    if (fseek(fp, posn, SEEK_SET) != 0)
+    if (fseeko(fp, posn, SEEK_SET) != 0)
         return UNKNOWN_ERROR;
 
     //mLFH.dump();
@@ -80,7 +76,7 @@
      * compressed size, and uncompressed size will be zero.  In practice
      * these seem to be rare.
      */
-    hasDD = (mLFH.mGPBitFlag & kUsesDataDescr) != 0;
+    bool hasDD = (mLFH.mGPBitFlag & kUsesDataDescr) != 0;
     if (hasDD) {
         // do something clever
         //ALOGD("+++ has data descriptor\n");
diff --git a/tools/zipalign/ZipFile.cpp b/tools/zipalign/ZipFile.cpp
index f2f65a6..42cc349 100644
--- a/tools/zipalign/ZipFile.cpp
+++ b/tools/zipalign/ZipFile.cpp
@@ -35,6 +35,8 @@
 #include <assert.h>
 #include <inttypes.h>
 
+_Static_assert(sizeof(off_t) == 8, "off_t too small");
+
 namespace android {
 
 /*
@@ -205,56 +207,43 @@
  */
 status_t ZipFile::readCentralDir(void)
 {
-    status_t result = OK;
-    uint8_t* buf = NULL;
-    off_t fileLength, seekStart;
-    long readAmount;
-    int i;
-
-    fseek(mZipFp, 0, SEEK_END);
-    fileLength = ftell(mZipFp);
+    fseeko(mZipFp, 0, SEEK_END);
+    off_t fileLength = ftello(mZipFp);
     rewind(mZipFp);
 
     /* too small to be a ZIP archive? */
     if (fileLength < EndOfCentralDir::kEOCDLen) {
-        ALOGD("Length is %ld -- too small\n", (long)fileLength);
-        result = INVALID_OPERATION;
-        goto bail;
+        ALOGD("Length is %lld -- too small\n", (long long) fileLength);
+        return INVALID_OPERATION;
     }
 
-    buf = new uint8_t[EndOfCentralDir::kMaxEOCDSearch];
-    if (buf == NULL) {
-        ALOGD("Failure allocating %d bytes for EOCD search",
-             EndOfCentralDir::kMaxEOCDSearch);
-        result = NO_MEMORY;
-        goto bail;
-    }
-
+    off_t seekStart;
+    size_t readAmount;
     if (fileLength > EndOfCentralDir::kMaxEOCDSearch) {
         seekStart = fileLength - EndOfCentralDir::kMaxEOCDSearch;
         readAmount = EndOfCentralDir::kMaxEOCDSearch;
     } else {
         seekStart = 0;
-        readAmount = (long) fileLength;
+        readAmount = fileLength;
     }
-    if (fseek(mZipFp, seekStart, SEEK_SET) != 0) {
-        ALOGD("Failure seeking to end of zip at %ld", (long) seekStart);
-        result = UNKNOWN_ERROR;
-        goto bail;
+    if (fseeko(mZipFp, seekStart, SEEK_SET) != 0) {
+        ALOGD("Failure seeking to end of zip at %lld", (long long) seekStart);
+        return UNKNOWN_ERROR;
     }
 
     /* read the last part of the file into the buffer */
-    if (fread(buf, 1, readAmount, mZipFp) != (size_t) readAmount) {
+    uint8_t buf[EndOfCentralDir::kMaxEOCDSearch];
+    if (fread(buf, 1, readAmount, mZipFp) != readAmount) {
         if (feof(mZipFp)) {
-            ALOGW("fread %ld bytes failed, unexpected EOF", readAmount);
+            ALOGW("fread %zu bytes failed, unexpected EOF", readAmount);
         } else {
-            ALOGW("fread %ld bytes failed, %s", readAmount, strerror(errno));
+            ALOGW("fread %zu bytes failed, %s", readAmount, strerror(errno));
         }
-        result = UNKNOWN_ERROR;
-        goto bail;
+        return UNKNOWN_ERROR;
     }
 
     /* find the end-of-central-dir magic */
+    int i;
     for (i = readAmount - 4; i >= 0; i--) {
         if (buf[i] == 0x50 &&
             ZipEntry::getLongLE(&buf[i]) == EndOfCentralDir::kSignature)
@@ -265,15 +254,14 @@
     }
     if (i < 0) {
         ALOGD("EOCD not found, not Zip\n");
-        result = INVALID_OPERATION;
-        goto bail;
+        return INVALID_OPERATION;
     }
 
     /* extract eocd values */
-    result = mEOCD.readBuf(buf + i, readAmount - i);
+    status_t result = mEOCD.readBuf(buf + i, readAmount - i);
     if (result != OK) {
-        ALOGD("Failure reading %ld bytes of EOCD values", readAmount - i);
-        goto bail;
+        ALOGD("Failure reading %zu bytes of EOCD values", readAmount - i);
+        return result;
     }
     //mEOCD.dump();
 
@@ -281,8 +269,7 @@
         mEOCD.mNumEntries != mEOCD.mTotalNumEntries)
     {
         ALOGD("Archive spanning not supported\n");
-        result = INVALID_OPERATION;
-        goto bail;
+        return INVALID_OPERATION;
     }
 
     /*
@@ -299,11 +286,10 @@
      * The only thing we really need right now is the file comment, which
      * we're hoping to preserve.
      */
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
         ALOGD("Failure seeking to central dir offset %" PRIu32 "\n",
              mEOCD.mCentralDirOffset);
-        result = UNKNOWN_ERROR;
-        goto bail;
+        return UNKNOWN_ERROR;
     }
 
     /*
@@ -318,7 +304,7 @@
         if (result != OK) {
             ALOGD("initFromCDE failed\n");
             delete pEntry;
-            goto bail;
+            return result;
         }
 
         mEntries.add(pEntry);
@@ -336,20 +322,16 @@
             } else {
                 ALOGW("fread EOCD failed, %s", strerror(errno));
             }
-            result = INVALID_OPERATION;
-            goto bail;
+            return INVALID_OPERATION;
         }
         if (ZipEntry::getLongLE(checkBuf) != EndOfCentralDir::kSignature) {
             ALOGD("EOCD read check failed\n");
-            result = UNKNOWN_ERROR;
-            goto bail;
+            return UNKNOWN_ERROR;
         }
         ALOGV("+++ EOCD read check passed\n");
     }
 
-bail:
-    delete[] buf;
-    return result;
+    return OK;
 }
 
 
@@ -370,9 +352,8 @@
 {
     ZipEntry* pEntry = NULL;
     status_t result = OK;
-    long lfhPosn, startPosn, endPosn, uncompressedLen;
-    FILE* inputFp = NULL;
-    uint32_t crc;
+    off_t lfhPosn, startPosn, endPosn, uncompressedLen;
+    uint32_t crc = 0;
     time_t modWhen;
 
     if (mReadOnly)
@@ -389,13 +370,14 @@
     if (getEntryByName(storageName) != NULL)
         return ALREADY_EXISTS;
 
+    FILE* inputFp = NULL;
     if (!data) {
         inputFp = fopen(fileName, FILE_OPEN_RO);
         if (inputFp == NULL)
             return errnoToStatus(errno);
     }
 
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -413,9 +395,9 @@
      * as a place-holder.  In theory the LFH isn't necessary, but in
      * practice some utilities demand it.
      */
-    lfhPosn = ftell(mZipFp);
+    lfhPosn = ftello(mZipFp);
     pEntry->mLFH.write(mZipFp);
-    startPosn = ftell(mZipFp);
+    startPosn = ftello(mZipFp);
 
     /*
      * Copy the data in, possibly compressing it as we go.
@@ -432,11 +414,11 @@
              * to be set through an API call, but I don't expect our
              * criteria to change over time.
              */
-            long src = inputFp ? ftell(inputFp) : size;
-            long dst = ftell(mZipFp) - startPosn;
+            off_t src = inputFp ? ftello(inputFp) : size;
+            off_t dst = ftello(mZipFp) - startPosn;
             if (dst + (dst / 10) > src) {
-                ALOGD("insufficient compression (src=%ld dst=%ld), storing\n",
-                    src, dst);
+                ALOGD("insufficient compression (src=%lld dst=%lld), storing\n",
+                    (long long) src, (long long) dst);
                 failed = true;
             }
         }
@@ -444,7 +426,7 @@
         if (failed) {
             compressionMethod = ZipEntry::kCompressStored;
             if (inputFp) rewind(inputFp);
-            fseek(mZipFp, startPosn, SEEK_SET);
+            fseeko(mZipFp, startPosn, SEEK_SET);
             /* fall through to kCompressStored case */
         }
     }
@@ -463,7 +445,7 @@
     }
 
     // currently seeked to end of file
-    uncompressedLen = inputFp ? ftell(inputFp) : size;
+    uncompressedLen = inputFp ? ftello(inputFp) : size;
 
     /*
      * We could write the "Data Descriptor", but there doesn't seem to
@@ -471,7 +453,7 @@
      *
      * Update file offsets.
      */
-    endPosn = ftell(mZipFp);            // seeked to end of compressed data
+    endPosn = ftello(mZipFp);            // seeked to end of compressed data
 
     /*
      * Success!  Fill out new values.
@@ -489,7 +471,7 @@
     /*
      * Go back and write the LFH.
      */
-    if (fseek(mZipFp, lfhPosn, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, lfhPosn, SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -522,7 +504,7 @@
 
     // Calculate where the entry payload offset will end up if we were to write
     // it as-is.
-    uint64_t expectedPayloadOffset = ftell(mZipFp) +
+    uint64_t expectedPayloadOffset = ftello(mZipFp) +
         android::ZipEntry::LocalFileHeader::kLFHLen +
         pEntry->mLFH.mFileNameLength +
         pEntry->mLFH.mExtraFieldLength;
@@ -548,7 +530,7 @@
 {
     ZipEntry* pEntry = NULL;
     status_t result;
-    long lfhPosn, endPosn;
+    off_t lfhPosn, endPosn;
 
     if (mReadOnly)
         return INVALID_OPERATION;
@@ -557,7 +539,7 @@
     assert(mZipFp != NULL);
     assert(mEntries.size() == mEOCD.mTotalNumEntries);
 
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -585,7 +567,7 @@
      * Write the LFH.  Since we're not recompressing the data, we already
      * have all of the fields filled out.
      */
-    lfhPosn = ftell(mZipFp);
+    lfhPosn = ftello(mZipFp);
     pEntry->mLFH.write(mZipFp);
 
     /*
@@ -595,8 +577,7 @@
      * fields as well.  This is a fixed-size area immediately following
      * the data.
      */
-    if (fseek(pSourceZip->mZipFp, pSourceEntry->getFileOffset(), SEEK_SET) != 0)
-    {
+    if (fseeko(pSourceZip->mZipFp, pSourceEntry->getFileOffset(), SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -617,7 +598,7 @@
     /*
      * Update file offsets.
      */
-    endPosn = ftell(mZipFp);
+    endPosn = ftello(mZipFp);
 
     /*
      * Success!  Fill out new values.
@@ -654,7 +635,7 @@
 {
     ZipEntry* pEntry = NULL;
     status_t result;
-    long lfhPosn, uncompressedLen;
+    off_t lfhPosn, uncompressedLen;
 
     if (mReadOnly)
         return INVALID_OPERATION;
@@ -663,7 +644,7 @@
     assert(mZipFp != NULL);
     assert(mEntries.size() == mEOCD.mTotalNumEntries);
 
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -688,7 +669,7 @@
      * as a place-holder.  In theory the LFH isn't necessary, but in
      * practice some utilities demand it.
      */
-    lfhPosn = ftell(mZipFp);
+    lfhPosn = ftello(mZipFp);
     pEntry->mLFH.write(mZipFp);
 
     /*
@@ -698,8 +679,7 @@
      * fields as well.  This is a fixed-size area immediately following
      * the data.
      */
-    if (fseek(pSourceZip->mZipFp, pSourceEntry->getFileOffset(), SEEK_SET) != 0)
-    {
+    if (fseeko(pSourceZip->mZipFp, pSourceEntry->getFileOffset(), SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -712,7 +692,7 @@
             result = NO_MEMORY;
             goto bail;
         }
-        long startPosn = ftell(mZipFp);
+        off_t startPosn = ftello(mZipFp);
         uint32_t crc;
         if (compressFpToFp(mZipFp, NULL, buf, uncompressedLen, &crc) != OK) {
             ALOGW("recompress of '%s' failed\n", pEntry->mCDE.mFileName);
@@ -720,13 +700,12 @@
             free(buf);
             goto bail;
         }
-        long endPosn = ftell(mZipFp);
+        off_t endPosn = ftello(mZipFp);
         pEntry->setDataInfo(uncompressedLen, endPosn - startPosn,
             pSourceEntry->getCRC32(), ZipEntry::kCompressDeflated);
         free(buf);
     } else {
-        off_t copyLen;
-        copyLen = pSourceEntry->getCompressedLen();
+        off_t copyLen = pSourceEntry->getCompressedLen();
         if ((pSourceEntry->mLFH.mGPBitFlag & ZipEntry::kUsesDataDescr) != 0)
             copyLen += ZipEntry::kDataDescriptorLen;
 
@@ -746,12 +725,12 @@
     mEOCD.mNumEntries++;
     mEOCD.mTotalNumEntries++;
     mEOCD.mCentralDirSize = 0;      // mark invalid; set by flush()
-    mEOCD.mCentralDirOffset = ftell(mZipFp);
+    mEOCD.mCentralDirOffset = ftello(mZipFp);
 
     /*
      * Go back and write the LFH.
      */
-    if (fseek(mZipFp, lfhPosn, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, lfhPosn, SEEK_SET) != 0) {
         result = UNKNOWN_ERROR;
         goto bail;
     }
@@ -978,7 +957,7 @@
 status_t ZipFile::flush(void)
 {
     status_t result = OK;
-    long eocdPosn;
+    off_t eocdPosn;
     int i, count;
 
     if (mReadOnly)
@@ -992,8 +971,7 @@
     if (result != OK)
         return result;
 
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0)
-        return UNKNOWN_ERROR;
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) return UNKNOWN_ERROR;
 
     count = mEntries.size();
     for (i = 0; i < count; i++) {
@@ -1001,7 +979,7 @@
         pEntry->mCDE.write(mZipFp);
     }
 
-    eocdPosn = ftell(mZipFp);
+    eocdPosn = ftello(mZipFp);
     mEOCD.mCentralDirSize = eocdPosn - mEOCD.mCentralDirOffset;
 
     mEOCD.write(mZipFp);
@@ -1011,8 +989,8 @@
      * with plain files, or if we deleted some entries, there's a lot
      * of wasted space at the end of the file.  Remove it now.
      */
-    if (ftruncate(fileno(mZipFp), ftell(mZipFp)) != 0) {
-        ALOGW("ftruncate failed %ld: %s\n", ftell(mZipFp), strerror(errno));
+    if (ftruncate(fileno(mZipFp), ftello(mZipFp)) != 0) {
+        ALOGW("ftruncate failed %lld: %s\n", (long long) ftello(mZipFp), strerror(errno));
         // not fatal
     }
 
@@ -1141,32 +1119,32 @@
             if (getSize > n)
                 getSize = n;
 
-            if (fseek(fp, (long) src, SEEK_SET) != 0) {
-                ALOGW("filemove src seek %ld failed, %s",
-                    (long) src, strerror(errno));
+            if (fseeko(fp, src, SEEK_SET) != 0) {
+                ALOGW("filemove src seek %lld failed, %s",
+                    (long long) src, strerror(errno));
                 return UNKNOWN_ERROR;
             }
 
             if (fread(readBuf, 1, getSize, fp) != getSize) {
                 if (feof(fp)) {
-                    ALOGW("fread %zu bytes off=%ld failed, unexpected EOF",
-                        getSize, (long) src);
+                    ALOGW("fread %zu bytes off=%lld failed, unexpected EOF",
+                        getSize, (long long) src);
                 } else {
-                    ALOGW("fread %zu bytes off=%ld failed, %s",
-                        getSize, (long) src, strerror(errno));
+                    ALOGW("fread %zu bytes off=%lld failed, %s",
+                        getSize, (long long) src, strerror(errno));
                 }
                 return UNKNOWN_ERROR;
             }
 
-            if (fseek(fp, (long) dst, SEEK_SET) != 0) {
-                ALOGW("filemove dst seek %ld failed, %s",
-                    (long) dst, strerror(errno));
+            if (fseeko(fp, dst, SEEK_SET) != 0) {
+                ALOGW("filemove dst seek %lld failed, %s",
+                    (long long) dst, strerror(errno));
                 return UNKNOWN_ERROR;
             }
 
             if (fwrite(readBuf, 1, getSize, fp) != getSize) {
-                ALOGW("filemove write %zu off=%ld failed, %s",
-                    getSize, (long) dst, strerror(errno));
+                ALOGW("filemove write %zu off=%lld failed, %s",
+                    getSize, (long long) dst, strerror(errno));
                 return UNKNOWN_ERROR;
             }
 
@@ -1263,10 +1241,10 @@
 
     bool ReadAtOffset(uint8_t* buf, size_t len, off64_t offset) const {
         // Data is usually requested sequentially, so this helps avoid pointless
-        // fseeks every time we perform a read. There's an impedence mismatch
+        // seeks every time we perform a read. There's an impedence mismatch
         // here because the original API was designed around pread and pwrite.
         if (offset != current_offset_) {
-            if (fseek(fp_, offset, SEEK_SET) != 0) {
+            if (fseeko(fp_, offset, SEEK_SET) != 0) {
                 return false;
             }
 
@@ -1298,10 +1276,10 @@
         return NULL;
     }
 
-    fseek(mZipFp, 0, SEEK_SET);
+    fseeko(mZipFp, 0, SEEK_SET);
 
     off_t offset = entry->getFileOffset();
-    if (fseek(mZipFp, offset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, offset, SEEK_SET) != 0) {
         goto bail;
     }
 
diff --git a/tools/ziptime/ZipEntry.cpp b/tools/ziptime/ZipEntry.cpp
index e7b52ed..c8eb377 100644
--- a/tools/ziptime/ZipEntry.cpp
+++ b/tools/ziptime/ZipEntry.cpp
@@ -43,19 +43,16 @@
  */
 status_t ZipEntry::initAndRewriteFromCDE(FILE* fp)
 {
-    status_t result;
-    long posn;
-
     /* read the CDE */
-    result = mCDE.rewrite(fp);
+    status_t result = mCDE.rewrite(fp);
     if (result != 0) {
         LOG("mCDE.rewrite failed\n");
         return result;
     }
 
     /* using the info in the CDE, go load up the LFH */
-    posn = ftell(fp);
-    if (fseek(fp, mCDE.mLocalHeaderRelOffset, SEEK_SET) != 0) {
+    off_t posn = ftello(fp);
+    if (fseeko(fp, mCDE.mLocalHeaderRelOffset, SEEK_SET) != 0) {
         LOG("local header seek failed (%" PRIu32 ")\n",
             mCDE.mLocalHeaderRelOffset);
         return -1;
@@ -67,7 +64,7 @@
         return result;
     }
 
-    if (fseek(fp, posn, SEEK_SET) != 0)
+    if (fseeko(fp, posn, SEEK_SET) != 0)
         return -1;
 
     return 0;
diff --git a/tools/ziptime/ZipFile.cpp b/tools/ziptime/ZipFile.cpp
index 1d111af..3002a65 100644
--- a/tools/ziptime/ZipFile.cpp
+++ b/tools/ziptime/ZipFile.cpp
@@ -40,8 +40,7 @@
     /* open the file */
     mZipFp = fopen(zipFileName, "r+b");
     if (mZipFp == NULL) {
-        int err = errno;
-        LOG("fopen failed: %d\n", err);
+        LOG("fopen \"%s\" failed: %s\n", zipFileName, strerror(errno));
         return -1;
     }
 
@@ -72,52 +71,39 @@
  */
 status_t ZipFile::rewriteCentralDir(void)
 {
-    status_t result = 0;
-    uint8_t* buf = NULL;
-    off_t fileLength, seekStart;
-    long readAmount;
-    int i;
-
-    fseek(mZipFp, 0, SEEK_END);
-    fileLength = ftell(mZipFp);
+    fseeko(mZipFp, 0, SEEK_END);
+    off_t fileLength = ftello(mZipFp);
     rewind(mZipFp);
 
     /* too small to be a ZIP archive? */
     if (fileLength < EndOfCentralDir::kEOCDLen) {
-        LOG("Length is %ld -- too small\n", (long)fileLength);
-        result = -1;
-        goto bail;
+        LOG("Length is %lld -- too small\n", (long long) fileLength);
+        return -1;
     }
 
-    buf = new uint8_t[EndOfCentralDir::kMaxEOCDSearch];
-    if (buf == NULL) {
-        LOG("Failure allocating %d bytes for EOCD search",
-             EndOfCentralDir::kMaxEOCDSearch);
-        result = -1;
-        goto bail;
-    }
-
+    off_t seekStart;
+    size_t readAmount;
     if (fileLength > EndOfCentralDir::kMaxEOCDSearch) {
         seekStart = fileLength - EndOfCentralDir::kMaxEOCDSearch;
         readAmount = EndOfCentralDir::kMaxEOCDSearch;
     } else {
         seekStart = 0;
-        readAmount = (long) fileLength;
+        readAmount = fileLength;
     }
-    if (fseek(mZipFp, seekStart, SEEK_SET) != 0) {
-        LOG("Failure seeking to end of zip at %ld", (long) seekStart);
-        result = -1;
-        goto bail;
+    if (fseeko(mZipFp, seekStart, SEEK_SET) != 0) {
+        LOG("Failure seeking to end of zip at %lld", (long long) seekStart);
+        return -1;
     }
 
     /* read the last part of the file into the buffer */
-    if (fread(buf, 1, readAmount, mZipFp) != (size_t) readAmount) {
-        LOG("short file? wanted %ld\n", readAmount);
-        result = -1;
-        goto bail;
+    uint8_t buf[EndOfCentralDir::kMaxEOCDSearch];
+    if (fread(buf, 1, readAmount, mZipFp) != readAmount) {
+        LOG("short file? wanted %zu\n", readAmount);
+        return -1;
     }
 
     /* find the end-of-central-dir magic */
+    int i;
     for (i = readAmount - 4; i >= 0; i--) {
         if (buf[i] == 0x50 &&
             ZipEntry::getLongLE(&buf[i]) == EndOfCentralDir::kSignature)
@@ -127,15 +113,14 @@
     }
     if (i < 0) {
         LOG("EOCD not found, not Zip\n");
-        result = -1;
-        goto bail;
+        return -1;
     }
 
     /* extract eocd values */
-    result = mEOCD.readBuf(buf + i, readAmount - i);
+    status_t result = mEOCD.readBuf(buf + i, readAmount - i);
     if (result != 0) {
-        LOG("Failure reading %ld bytes of EOCD values", readAmount - i);
-        goto bail;
+        LOG("Failure reading %zu bytes of EOCD values", readAmount - i);
+        return result;
     }
 
     /*
@@ -152,49 +137,39 @@
      * The only thing we really need right now is the file comment, which
      * we're hoping to preserve.
      */
-    if (fseek(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
+    if (fseeko(mZipFp, mEOCD.mCentralDirOffset, SEEK_SET) != 0) {
         LOG("Failure seeking to central dir offset %" PRIu32 "\n",
              mEOCD.mCentralDirOffset);
-        result = -1;
-        goto bail;
+        return -1;
     }
 
     /*
      * Loop through and read the central dir entries.
      */
-    int entry;
-    for (entry = 0; entry < mEOCD.mTotalNumEntries; entry++) {
+    for (int entry = 0; entry < mEOCD.mTotalNumEntries; entry++) {
         ZipEntry* pEntry = new ZipEntry;
-
         result = pEntry->initAndRewriteFromCDE(mZipFp);
+        delete pEntry;
         if (result != 0) {
             LOG("initFromCDE failed\n");
-            delete pEntry;
-            goto bail;
+            return -1;
         }
-
-        delete pEntry;
     }
 
-
     /*
      * If all went well, we should now be back at the EOCD.
      */
     uint8_t checkBuf[4];
     if (fread(checkBuf, 1, 4, mZipFp) != 4) {
         LOG("EOCD check read failed\n");
-        result = -1;
-        goto bail;
+        return -1;
     }
     if (ZipEntry::getLongLE(checkBuf) != EndOfCentralDir::kSignature) {
         LOG("EOCD read check failed\n");
-        result = -1;
-        goto bail;
+        return -1;
     }
 
-bail:
-    delete[] buf;
-    return result;
+    return 0;
 }
 
 /*