Revert "Revert "releasetools: Support OTAs that have OEM properties changes.""

This CL fixes the bug in [1] (copy-paste error) and reenables it.

We need to handle a special case that an OTA goes from a source build
without OEM properties to a target build with those properties (or vice
versa). Add support in OTA scripts to deal the case properly, by a)
using two oem_props variables to handle source and target builds
respectively; b) adjusting the fingerprint/thumbprint assertions to
allow a mix of both.

[1] commit c086370440

Change-Id: I98118d77d5a0ff694fa1ee33602b5ee5e048599b
This commit is contained in:
Tao Bao 2016-03-15 13:20:19 -07:00
parent 3c37889299
commit 3e30d97dde
2 changed files with 67 additions and 40 deletions

View File

@ -118,6 +118,17 @@ class EdifyGenerator(object):
" or ".join(fp)) " or ".join(fp))
self.script.append(cmd) self.script.append(cmd)
def AssertFingerprintOrThumbprint(self, fp, tp):
"""Assert that the current recovery build fingerprint is fp, or thumbprint
is tp."""
cmd = ('getprop("ro.build.fingerprint") == "{fp}" ||\n'
' getprop("ro.build.thumbprint") == "{tp}" ||\n'
' abort("Package expects build fingerprint of {fp} or '
'thumbprint of {tp}; this device has a fingerprint of " '
'+ getprop("ro.build.fingerprint") and a thumbprint of " '
'+ getprop("ro.build.thumbprint") + ".");').format(fp=fp, tp=tp)
self.script.append(cmd)
def AssertOlderBuild(self, timestamp, timestamp_text): def AssertOlderBuild(self, timestamp, timestamp_text):
"""Assert that the build on the device is older (or the same as) """Assert that the build on the device is older (or the same as)
the given timestamp.""" the given timestamp."""

View File

@ -439,7 +439,7 @@ def SignOutput(temp_zip_name, output_zip_name):
def AppendAssertions(script, info_dict, oem_dict=None): def AppendAssertions(script, info_dict, oem_dict=None):
oem_props = info_dict.get("oem_fingerprint_properties") oem_props = info_dict.get("oem_fingerprint_properties")
if oem_props is None or len(oem_props) == 0: if not oem_props:
device = GetBuildProp("ro.product.device", info_dict) device = GetBuildProp("ro.product.device", info_dict)
script.AssertDevice(device) script.AssertDevice(device)
else: else:
@ -528,10 +528,10 @@ def WriteFullOTAPackage(input_zip, output_zip):
# in the target build. # in the target build.
script = edify_generator.EdifyGenerator(3, OPTIONS.info_dict) script = edify_generator.EdifyGenerator(3, OPTIONS.info_dict)
oem_props = OPTIONS.info_dict.get("oem_fingerprint_properties")
recovery_mount_options = OPTIONS.info_dict.get("recovery_mount_options") recovery_mount_options = OPTIONS.info_dict.get("recovery_mount_options")
oem_props = OPTIONS.info_dict.get("oem_fingerprint_properties")
oem_dict = None oem_dict = None
if oem_props is not None and len(oem_props) > 0: if oem_props:
if OPTIONS.oem_source is None: if OPTIONS.oem_source is None:
raise common.ExternalError("OEM source required for this build") raise common.ExternalError("OEM source required for this build")
if not OPTIONS.oem_no_mount: if not OPTIONS.oem_no_mount:
@ -539,9 +539,9 @@ def WriteFullOTAPackage(input_zip, output_zip):
oem_dict = common.LoadDictionaryFromLines( oem_dict = common.LoadDictionaryFromLines(
open(OPTIONS.oem_source).readlines()) open(OPTIONS.oem_source).readlines())
target_fp = CalculateFingerprint(oem_props, oem_dict, OPTIONS.info_dict)
metadata = { metadata = {
"post-build": CalculateFingerprint(oem_props, oem_dict, "post-build": target_fp,
OPTIONS.info_dict),
"pre-device": GetOemProperty("ro.product.device", oem_props, oem_dict, "pre-device": GetOemProperty("ro.product.device", oem_props, oem_dict,
OPTIONS.info_dict), OPTIONS.info_dict),
"post-timestamp": GetBuildProp("ro.build.date.utc", OPTIONS.info_dict), "post-timestamp": GetBuildProp("ro.build.date.utc", OPTIONS.info_dict),
@ -610,8 +610,7 @@ else if get_stage("%(bcb_dev)s") == "3/3" then
""" % bcb_dev) """ % bcb_dev)
# Dump fingerprints # Dump fingerprints
script.Print("Target: %s" % CalculateFingerprint( script.Print("Target: %s" % target_fp)
oem_props, oem_dict, OPTIONS.info_dict))
device_specific.FullOTA_InstallBegin() device_specific.FullOTA_InstallBegin()
@ -773,17 +772,18 @@ def WriteBlockIncrementalOTAPackage(target_zip, source_zip, output_zip):
target_version = OPTIONS.target_info_dict["recovery_api_version"] target_version = OPTIONS.target_info_dict["recovery_api_version"]
if source_version == 0: if source_version == 0:
print ("WARNING: generating edify script for a source that " print("WARNING: generating edify script for a source that "
"can't install it.") "can't install it.")
script = edify_generator.EdifyGenerator( script = edify_generator.EdifyGenerator(
source_version, OPTIONS.target_info_dict, source_version, OPTIONS.target_info_dict,
fstab=OPTIONS.source_info_dict["fstab"]) fstab=OPTIONS.source_info_dict["fstab"])
oem_props = OPTIONS.info_dict.get("oem_fingerprint_properties")
recovery_mount_options = OPTIONS.source_info_dict.get( recovery_mount_options = OPTIONS.source_info_dict.get(
"recovery_mount_options") "recovery_mount_options")
source_oem_props = OPTIONS.source_info_dict.get("oem_fingerprint_properties")
target_oem_props = OPTIONS.target_info_dict.get("oem_fingerprint_properties")
oem_dict = None oem_dict = None
if oem_props is not None and len(oem_props) > 0: if source_oem_props or target_oem_props:
if OPTIONS.oem_source is None: if OPTIONS.oem_source is None:
raise common.ExternalError("OEM source required for this build") raise common.ExternalError("OEM source required for this build")
if not OPTIONS.oem_no_mount: if not OPTIONS.oem_no_mount:
@ -792,8 +792,8 @@ def WriteBlockIncrementalOTAPackage(target_zip, source_zip, output_zip):
open(OPTIONS.oem_source).readlines()) open(OPTIONS.oem_source).readlines())
metadata = { metadata = {
"pre-device": GetOemProperty("ro.product.device", oem_props, oem_dict, "pre-device": GetOemProperty("ro.product.device", source_oem_props,
OPTIONS.source_info_dict), oem_dict, OPTIONS.source_info_dict),
"ota-type": "BLOCK", "ota-type": "BLOCK",
} }
@ -828,9 +828,9 @@ def WriteBlockIncrementalOTAPackage(target_zip, source_zip, output_zip):
metadata=metadata, metadata=metadata,
info_dict=OPTIONS.source_info_dict) info_dict=OPTIONS.source_info_dict)
source_fp = CalculateFingerprint(oem_props, oem_dict, source_fp = CalculateFingerprint(source_oem_props, oem_dict,
OPTIONS.source_info_dict) OPTIONS.source_info_dict)
target_fp = CalculateFingerprint(oem_props, oem_dict, target_fp = CalculateFingerprint(target_oem_props, oem_dict,
OPTIONS.target_info_dict) OPTIONS.target_info_dict)
metadata["pre-build"] = source_fp metadata["pre-build"] = source_fp
metadata["post-build"] = target_fp metadata["post-build"] = target_fp
@ -926,32 +926,39 @@ else if get_stage("%(bcb_dev)s") != "3/3" then
""" % bcb_dev) """ % bcb_dev)
# Dump fingerprints # Dump fingerprints
script.Print("Source: %s" % CalculateFingerprint( script.Print(source_fp)
oem_props, oem_dict, OPTIONS.source_info_dict)) script.Print(target_fp)
script.Print("Target: %s" % CalculateFingerprint(
oem_props, oem_dict, OPTIONS.target_info_dict))
script.Print("Verifying current system...") script.Print("Verifying current system...")
device_specific.IncrementalOTA_VerifyBegin() device_specific.IncrementalOTA_VerifyBegin()
if oem_props is None: # When blockimgdiff version is less than 3 (non-resumable block-based OTA),
# When blockimgdiff version is less than 3 (non-resumable block-based OTA), # patching on a device that's already on the target build will damage the
# patching on a device that's already on the target build will damage the # system. Because operations like move don't check the block state, they
# system. Because operations like move don't check the block state, they # always apply the changes unconditionally.
# always apply the changes unconditionally. if blockimgdiff_version <= 2:
if blockimgdiff_version <= 2: if source_oem_props is None:
script.AssertSomeFingerprint(source_fp) script.AssertSomeFingerprint(source_fp)
else: else:
script.AssertSomeFingerprint(source_fp, target_fp)
else:
if blockimgdiff_version <= 2:
script.AssertSomeThumbprint( script.AssertSomeThumbprint(
GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict)) GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict))
else:
else: # blockimgdiff_version > 2
if source_oem_props is None and target_oem_props is None:
script.AssertSomeFingerprint(source_fp, target_fp)
elif source_oem_props is not None and target_oem_props is not None:
script.AssertSomeThumbprint( script.AssertSomeThumbprint(
GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict), GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict),
GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict)) GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict))
elif source_oem_props is None and target_oem_props is not None:
script.AssertFingerprintOrThumbprint(
source_fp,
GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict))
else:
script.AssertFingerprintOrThumbprint(
target_fp,
GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict))
# Check the required cache size (i.e. stashed blocks). # Check the required cache size (i.e. stashed blocks).
size = [] size = []
@ -1074,7 +1081,7 @@ def WriteVerifyPackage(input_zip, output_zip):
recovery_mount_options = OPTIONS.info_dict.get( recovery_mount_options = OPTIONS.info_dict.get(
"recovery_mount_options") "recovery_mount_options")
oem_dict = None oem_dict = None
if oem_props is not None and len(oem_props) > 0: if oem_props:
if OPTIONS.oem_source is None: if OPTIONS.oem_source is None:
raise common.ExternalError("OEM source required for this build") raise common.ExternalError("OEM source required for this build")
if not OPTIONS.oem_no_mount: if not OPTIONS.oem_no_mount:
@ -1417,17 +1424,18 @@ def WriteIncrementalOTAPackage(target_zip, source_zip, output_zip):
target_version = OPTIONS.target_info_dict["recovery_api_version"] target_version = OPTIONS.target_info_dict["recovery_api_version"]
if source_version == 0: if source_version == 0:
print ("WARNING: generating edify script for a source that " print("WARNING: generating edify script for a source that "
"can't install it.") "can't install it.")
script = edify_generator.EdifyGenerator( script = edify_generator.EdifyGenerator(
source_version, OPTIONS.target_info_dict, source_version, OPTIONS.target_info_dict,
fstab=OPTIONS.source_info_dict["fstab"]) fstab=OPTIONS.source_info_dict["fstab"])
oem_props = OPTIONS.info_dict.get("oem_fingerprint_properties")
recovery_mount_options = OPTIONS.source_info_dict.get( recovery_mount_options = OPTIONS.source_info_dict.get(
"recovery_mount_options") "recovery_mount_options")
source_oem_props = OPTIONS.source_info_dict.get("oem_fingerprint_properties")
target_oem_props = OPTIONS.target_info_dict.get("oem_fingerprint_properties")
oem_dict = None oem_dict = None
if oem_props is not None and len(oem_props) > 0: if source_oem_props or target_oem_props:
if OPTIONS.oem_source is None: if OPTIONS.oem_source is None:
raise common.ExternalError("OEM source required for this build") raise common.ExternalError("OEM source required for this build")
if not OPTIONS.oem_no_mount: if not OPTIONS.oem_no_mount:
@ -1436,8 +1444,8 @@ def WriteIncrementalOTAPackage(target_zip, source_zip, output_zip):
open(OPTIONS.oem_source).readlines()) open(OPTIONS.oem_source).readlines())
metadata = { metadata = {
"pre-device": GetOemProperty("ro.product.device", oem_props, oem_dict, "pre-device": GetOemProperty("ro.product.device", source_oem_props,
OPTIONS.source_info_dict), oem_dict, OPTIONS.source_info_dict),
"ota-type": "FILE", "ota-type": "FILE",
} }
@ -1480,17 +1488,25 @@ def WriteIncrementalOTAPackage(target_zip, source_zip, output_zip):
else: else:
vendor_diff = None vendor_diff = None
target_fp = CalculateFingerprint(oem_props, oem_dict, target_fp = CalculateFingerprint(target_oem_props, oem_dict,
OPTIONS.target_info_dict) OPTIONS.target_info_dict)
source_fp = CalculateFingerprint(oem_props, oem_dict, source_fp = CalculateFingerprint(source_oem_props, oem_dict,
OPTIONS.source_info_dict) OPTIONS.source_info_dict)
if oem_props is None: if source_oem_props is None and target_oem_props is None:
script.AssertSomeFingerprint(source_fp, target_fp) script.AssertSomeFingerprint(source_fp, target_fp)
else: elif source_oem_props is not None and target_oem_props is not None:
script.AssertSomeThumbprint( script.AssertSomeThumbprint(
GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict), GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict),
GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict)) GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict))
elif source_oem_props is None and target_oem_props is not None:
script.AssertFingerprintOrThumbprint(
source_fp,
GetBuildProp("ro.build.thumbprint", OPTIONS.target_info_dict))
else:
script.AssertFingerprintOrThumbprint(
target_fp,
GetBuildProp("ro.build.thumbprint", OPTIONS.source_info_dict))
metadata["pre-build"] = source_fp metadata["pre-build"] = source_fp
metadata["post-build"] = target_fp metadata["post-build"] = target_fp