diff options
author | Daniel Zheng <zhengdaniel@google.com> | 2024-01-30 21:32:15 +0000 |
---|---|---|
committer | Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com> | 2024-01-30 21:32:15 +0000 |
commit | 0eaf2ea59d6a109ab22c73bb1beb1dfcf653c793 (patch) | |
tree | 638a1c17bf5d303cc7cae0d5f26bcf40caa82128 | |
parent | 60e7047cf25d06accf79b1b13bc9860746584b31 (diff) | |
parent | 0dc25a67793c18f53bcd2e7787162be4e17898db (diff) | |
download | update_engine-0eaf2ea59d6a109ab22c73bb1beb1dfcf653c793.tar.gz |
update_engine: refactor into method am: 0dc25a6779
Original change: https://android-review.googlesource.com/c/platform/system/update_engine/+/2932913
Change-Id: Id5c123cbc026ed57ebc81d4379b81f4782c1ede4
Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
-rw-r--r-- | payload_consumer/delta_performer.cc | 125 | ||||
-rw-r--r-- | payload_consumer/delta_performer.h | 2 |
2 files changed, 69 insertions, 58 deletions
diff --git a/payload_consumer/delta_performer.cc b/payload_consumer/delta_performer.cc index 8083cb19..fe263c2a 100644 --- a/payload_consumer/delta_performer.cc +++ b/payload_consumer/delta_performer.cc @@ -646,65 +646,10 @@ bool DeltaPerformer::Write(const void* bytes, size_t count, ErrorCode* error) { // Check whether we received all of the next operation's data payload. if (!CanPerformInstallOperation(op)) return true; - - // Validate the operation unconditionally. This helps prevent the - // exploitation of vulnerabilities in the patching libraries, e.g. bspatch. - // The hash of the patch data for a given operation is embedded in the - // payload metadata; and thus has been verified against the public key on - // device. - // Note: Validate must be called only if CanPerformInstallOperation is - // called. Otherwise, we might be failing operations before even if there - // isn't sufficient data to compute the proper hash. - *error = ValidateOperationHash(op); - if (*error != ErrorCode::kSuccess) { - if (install_plan_->hash_checks_mandatory) { - LOG(ERROR) << "Mandatory operation hash check failed"; - return false; - } - - // For non-mandatory cases, just send a UMA stat. - LOG(WARNING) << "Ignoring operation validation errors"; - *error = ErrorCode::kSuccess; - } - - // Makes sure we unblock exit when this operation completes. - ScopedTerminatorExitUnblocker exit_unblocker = - ScopedTerminatorExitUnblocker(); // Avoids a compiler unused var bug. - - base::TimeTicks op_start_time = base::TimeTicks::Now(); - - bool op_result{}; - const string op_name = InstallOperationTypeName(op.type()); - switch (op.type()) { - case InstallOperation::REPLACE: - case InstallOperation::REPLACE_BZ: - case InstallOperation::REPLACE_XZ: - op_result = PerformReplaceOperation(op); - OP_DURATION_HISTOGRAM("REPLACE", op_start_time); - break; - case InstallOperation::ZERO: - case InstallOperation::DISCARD: - op_result = PerformZeroOrDiscardOperation(op); - OP_DURATION_HISTOGRAM("ZERO_OR_DISCARD", op_start_time); - break; - case InstallOperation::SOURCE_COPY: - op_result = PerformSourceCopyOperation(op, error); - OP_DURATION_HISTOGRAM("SOURCE_COPY", op_start_time); - break; - case InstallOperation::SOURCE_BSDIFF: - case InstallOperation::BROTLI_BSDIFF: - case InstallOperation::PUFFDIFF: - case InstallOperation::ZUCCHINI: - case InstallOperation::LZ4DIFF_PUFFDIFF: - case InstallOperation::LZ4DIFF_BSDIFF: - op_result = PerformDiffOperation(op, error); - OP_DURATION_HISTOGRAM(op_name, op_start_time); - break; - default: - op_result = false; - } - if (!HandleOpResult(op_result, op_name.c_str(), error)) + if (!ProcessOperation(&op, error)) { + LOG(ERROR) << "unable to process operation: " << *error; return false; + } next_operation_num_++; UpdateOverallProgress(false, "Completed "); @@ -748,6 +693,70 @@ bool DeltaPerformer::Write(const void* bytes, size_t count, ErrorCode* error) { return true; } +bool DeltaPerformer::ProcessOperation(const InstallOperation* op, + ErrorCode* error) { + // Validate the operation unconditionally. This helps prevent the + // exploitation of vulnerabilities in the patching libraries, e.g. bspatch. + // The hash of the patch data for a given operation is embedded in the + // payload metadata; and thus has been verified against the public key on + // device. + // Note: Validate must be called only if CanPerformInstallOperation is + // called. Otherwise, we might be failing operations before even if there + // isn't sufficient data to compute the proper hash. + *error = ValidateOperationHash(*op); + if (*error != ErrorCode::kSuccess) { + if (install_plan_->hash_checks_mandatory) { + LOG(ERROR) << "Mandatory operation hash check failed"; + return false; + } + + // For non-mandatory cases, just send a UMA stat. + LOG(WARNING) << "Ignoring operation validation errors"; + *error = ErrorCode::kSuccess; + } + + // Makes sure we unblock exit when this operation completes. + ScopedTerminatorExitUnblocker exit_unblocker = + ScopedTerminatorExitUnblocker(); // Avoids a compiler unused var bug. + + base::TimeTicks op_start_time = base::TimeTicks::Now(); + + bool op_result{}; + const string op_name = InstallOperationTypeName(op->type()); + switch (op->type()) { + case InstallOperation::REPLACE: + case InstallOperation::REPLACE_BZ: + case InstallOperation::REPLACE_XZ: + op_result = PerformReplaceOperation(*op); + OP_DURATION_HISTOGRAM("REPLACE", op_start_time); + break; + case InstallOperation::ZERO: + case InstallOperation::DISCARD: + op_result = PerformZeroOrDiscardOperation(*op); + OP_DURATION_HISTOGRAM("ZERO_OR_DISCARD", op_start_time); + break; + case InstallOperation::SOURCE_COPY: + op_result = PerformSourceCopyOperation(*op, error); + OP_DURATION_HISTOGRAM("SOURCE_COPY", op_start_time); + break; + case InstallOperation::SOURCE_BSDIFF: + case InstallOperation::BROTLI_BSDIFF: + case InstallOperation::PUFFDIFF: + case InstallOperation::ZUCCHINI: + case InstallOperation::LZ4DIFF_PUFFDIFF: + case InstallOperation::LZ4DIFF_BSDIFF: + op_result = PerformDiffOperation(*op, error); + OP_DURATION_HISTOGRAM(op_name, op_start_time); + break; + default: + op_result = false; + } + if (!HandleOpResult(op_result, op_name.c_str(), error)) + return false; + + return true; +} + bool DeltaPerformer::IsManifestValid() { return manifest_valid_; } diff --git a/payload_consumer/delta_performer.h b/payload_consumer/delta_performer.h index e83e000b..1584dc63 100644 --- a/payload_consumer/delta_performer.h +++ b/payload_consumer/delta_performer.h @@ -246,6 +246,8 @@ class DeltaPerformer : public FileWriter { // to be able to perform a given install operation. bool CanPerformInstallOperation(const InstallOperation& operation); + // Process one InstallOperation + bool ProcessOperation(const InstallOperation* op, ErrorCode* error); // Checks the integrity of the payload manifest. Returns true upon success, // false otherwise. ErrorCode ValidateManifest(); |