Add common verified boot tools and library.

This code is originally from the Brillo project but has been adapted for
use in all of Android. It consists of a tool - avbtool - for working
with images (e.g. boot.img, system.img). See the README file for how
it's integrated into the Android build system and how to enable it.

The main job of avbtool is to create vbmeta.img which is the
top-level object for verified boot. This image is designed to go into
the vbmeta partition (or, if using A/B, the slot in question
e.g. vbmeta_a or vbmeta_b) and be of minimal size (for out-of-band
updates). The vbmeta image is cryptographically signed and contains
verification data (e.g. cryptographic digests) for verifying boot.img,
system.img, and other partitions/images.

The vbmeta image can also contain references to other partitions where
verification data is stored as well as a public key indicating who
should sign the verification data. This indirection provides
delegation, that is, it allows a 3rd party to control content on a given
partition by including the public key said 3rd party is using to sign
the data with, in vbmeta.img. By design, this authority can be easily
revoked by simply updating vbmeta.img with new descriptors for the
partition in question.

Storing signed verification data on other images - for example
boot.img and system.img - is also done with avbtool.

In addition to avbtool, a library - libavb - is provided. This library
performs all verification on the device side e.g. it starts by loading
the vbmeta partition, checks the signature, and then goes on to load
the boot partition for verification.

The libavb library is intended to be used in both boot loaders and
inside Android. It has a simple abstraction for system dependencies
(see libavb/avb_sysdeps.h) as well as operations that the boot loader
or OS is expected to implement (see libavb/avb_ops.h).

In addition to handling verified boot, libavb will in the future be
extended to handle A/B selection in a way that can be used in the
device's fastboot implementation, its boot loader, and its
boot_control HAL implementation. This will be implemented in a future
CL.

BUG=29414516
TEST=Unit tests for avbtool and libavb + unit tests pass.

Change-Id: I69ee86878e21fa718faccfc56eb0b1f40707d847
diff --git a/libavb/avb_descriptor.c b/libavb/avb_descriptor.c
new file mode 100644
index 0000000..f8bc3a2
--- /dev/null
+++ b/libavb/avb_descriptor.c
@@ -0,0 +1,151 @@
+/*
+ * Copyright (C) 2016 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.
+ */
+
+#include "avb_descriptor.h"
+#include "avb_util.h"
+#include "avb_vbmeta_image.h"
+
+bool avb_descriptor_validate_and_byteswap(const AvbDescriptor* src,
+                                          AvbDescriptor* dest) {
+  dest->tag = avb_be64toh(src->tag);
+  dest->num_bytes_following = avb_be64toh(src->num_bytes_following);
+
+  if ((dest->num_bytes_following & 0x07) != 0) {
+    avb_error("Descriptor size is not divisible by 8.\n");
+    return false;
+  }
+  return true;
+}
+
+bool avb_descriptor_foreach(const uint8_t* image_data, size_t image_size,
+                            AvbDescriptorForeachFunc foreach_func,
+                            void* user_data) {
+  const AvbVBMetaImageHeader* header = NULL;
+  bool ret = false;
+  const uint8_t* image_end;
+  const uint8_t* desc_start;
+  const uint8_t* desc_end;
+  const uint8_t* p;
+
+  if (image_data == NULL) {
+    avb_error("image_data is NULL\n.");
+    goto out;
+  }
+
+  if (foreach_func == NULL) {
+    avb_error("foreach_func is NULL\n.");
+    goto out;
+  }
+
+  if (image_size < sizeof(AvbVBMetaImageHeader)) {
+    avb_error("Length is smaller than header.\n");
+    goto out;
+  }
+
+  /* Ensure magic is correct. */
+  if (avb_memcmp(image_data, AVB_MAGIC, AVB_MAGIC_LEN) != 0) {
+    avb_error("Magic is incorrect.\n");
+    goto out;
+  }
+
+  /* Careful, not byteswapped - also ensure it's aligned properly. */
+  avb_assert_word_aligned(image_data);
+  header = (const AvbVBMetaImageHeader*)image_data;
+  image_end = image_data + image_size;
+
+  desc_start = image_data + sizeof(AvbVBMetaImageHeader) +
+               avb_be64toh(header->authentication_data_block_size) +
+               avb_be64toh(header->descriptors_offset);
+
+  desc_end = desc_start + avb_be64toh(header->descriptors_size);
+
+  if (desc_start < image_data || desc_start > image_end ||
+      desc_end < image_data || desc_end > image_end || desc_end < desc_start) {
+    avb_error("Descriptors not inside passed-in data.\n");
+    goto out;
+  }
+
+  for (p = desc_start; p < desc_end;) {
+    const AvbDescriptor* dh = (const AvbDescriptor*)p;
+    avb_assert_word_aligned(dh);
+    uint64_t nb_following = avb_be64toh(dh->num_bytes_following);
+    uint64_t nb_total = sizeof(AvbDescriptor) + nb_following;
+
+    if ((nb_total & 7) != 0) {
+      avb_error("Invalid descriptor length.\n");
+      goto out;
+    }
+
+    if (nb_total + p < desc_start || nb_total + p > desc_end) {
+      avb_error("Invalid data in descriptors array.\n");
+      goto out;
+    }
+
+    if (foreach_func(dh, user_data) == 0) {
+      goto out;
+    }
+
+    p += nb_total;
+  }
+
+  ret = true;
+
+out:
+  return ret;
+}
+
+static bool count_descriptors(const AvbDescriptor* descriptor,
+                              void* user_data) {
+  size_t* num_descriptors = user_data;
+  *num_descriptors += 1;
+  return true;
+}
+
+typedef struct {
+  size_t descriptor_number;
+  const AvbDescriptor** descriptors;
+} SetDescriptorData;
+
+static bool set_descriptors(const AvbDescriptor* descriptor, void* user_data) {
+  SetDescriptorData* data = user_data;
+  data->descriptors[data->descriptor_number++] = descriptor;
+  return true;
+}
+
+const AvbDescriptor** avb_descriptor_get_all(const uint8_t* image_data,
+                                             size_t image_size,
+                                             size_t* out_num_descriptors) {
+  size_t num_descriptors = 0;
+  SetDescriptorData data;
+
+  avb_descriptor_foreach(image_data, image_size, count_descriptors,
+                         &num_descriptors);
+
+  data.descriptor_number = 0;
+  data.descriptors =
+      avb_calloc(sizeof(const AvbDescriptor*) * (num_descriptors + 1));
+  if (data.descriptors == NULL) {
+    return NULL;
+  }
+  avb_descriptor_foreach(image_data, image_size, set_descriptors, &data);
+  avb_assert(data.descriptor_number == num_descriptors);
+
+  if (out_num_descriptors != NULL) {
+    *out_num_descriptors = num_descriptors;
+  }
+
+  return data.descriptors;
+}