OSDN Git Service

Merge "libfec: correct verity table only if it's invalid"
authorTreehugger Robot <treehugger-gerrit@google.com>
Thu, 20 Oct 2016 18:16:52 +0000 (18:16 +0000)
committerGerrit Code Review <noreply-gerritcodereview@google.com>
Thu, 20 Oct 2016 18:16:52 +0000 (18:16 +0000)
libfec/fec_verity.cpp

index 5dea53d..3f636dd 100644 (file)
@@ -312,6 +312,11 @@ static int verify_tree(fec_handle *f, const uint8_t *root)
 
     debug("valid");
 
+    if (v->hash) {
+        delete[] v->hash;
+        v->hash = NULL;
+    }
+
     v->hash = data_hashes.release();
     return 0;
 }
@@ -319,7 +324,7 @@ static int verify_tree(fec_handle *f, const uint8_t *root)
 /* reads, corrects and parses the verity table, validates parameters, and if
    `f->flags' does not have `FEC_VERITY_DISABLE' set, calls `verify_tree' to
    load and validate the hash tree */
-static int parse_table(fec_handle *f, uint64_t offset, uint32_t size)
+static int parse_table(fec_handle *f, uint64_t offset, uint32_t size, bool useecc)
 {
     check(f);
     check(size >= VERITY_MIN_TABLE_SIZE);
@@ -335,8 +340,13 @@ static int parse_table(fec_handle *f, uint64_t offset, uint32_t size)
         return -1;
     }
 
-    if (fec_pread(f, table.get(), size, offset) != (ssize_t)size) {
-        error("failed to read verity table: %s", strerror(errno));
+    if (!useecc) {
+        if (!raw_pread(f, table.get(), size, offset)) {
+            error("failed to read verity table: %s", strerror(errno));
+            return -1;
+        }
+    } else if (fec_pread(f, table.get(), size, offset) != (ssize_t)size) {
+        error("failed to ecc read verity table: %s", strerror(errno));
         return -1;
     }
 
@@ -430,7 +440,18 @@ static int parse_table(fec_handle *f, uint64_t offset, uint32_t size)
         check(v->data_blocks == v->hash_start / FEC_BLOCKSIZE);
     }
 
+    if (v->salt) {
+        delete[] v->salt;
+        v->salt = NULL;
+    }
+
     v->salt = salt.release();
+
+    if (v->table) {
+        delete[] v->table;
+        v->table = NULL;
+    }
+
     v->table = table.release();
 
     if (!(f->flags & FEC_VERITY_DISABLE)) {
@@ -589,7 +610,10 @@ int verity_parse_header(fec_handle *f, uint64_t offset)
 
     v->metadata_start = offset;
 
-    if (parse_table(f, offset + sizeof(v->header), v->header.length) == -1) {
+    if (parse_table(f, offset + sizeof(v->header), v->header.length,
+            false) == -1 &&
+        parse_table(f, offset + sizeof(v->header), v->header.length,
+            true)  == -1) {
         return -1;
     }