diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..d6dd317
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,11 @@
+# Build/test generated files
+/*.pub.pem
+/app.info
+/delta_generator
+/html/
+/test_http_server
+/update_engine
+/update_engine.dbusclient.h
+/update_engine.dbusserver.h
+/update_engine_client
+/update_engine_unittests
diff --git a/Android.mk b/Android.mk
new file mode 100644
index 0000000..265ed23
--- /dev/null
+++ b/Android.mk
@@ -0,0 +1,484 @@
+#
+# Copyright (C) 2015 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.
+#
+
+LOCAL_PATH := $(my-dir)
+
+# Default values for the USE flags. Override these USE flags from your product.
+BRILLO_USE_DBUS ?= 1
+BRILLO_USE_HWID_OVERRIDE ?= 0
+BRILLO_USE_MTD ?= 0
+BRILLO_USE_POWER_MANAGEMENT ?= 0
+
+ue_common_cflags := \
+    -DUSE_DBUS=$(BRILLO_USE_DBUS) \
+    -DUSE_HWID_OVERRIDE=$(BRILLO_USE_HWID_OVERRIDE) \
+    -DUSE_MTD=$(BRILLO_USE_MTD) \
+    -DUSE_POWER_MANAGEMENT=$(BRILLO_USE_POWER_MANAGEMENT) \
+    -D_FILE_OFFSET_BITS=64 \
+    -D_POSIX_C_SOURCE=199309L \
+    -Wa,--noexecstack \
+    -Wall \
+    -Werror \
+    -Wextra \
+    -Wformat=2 \
+    -Wno-psabi \
+    -Wno-unused-parameter \
+    -ffunction-sections \
+    -fstack-protector-strong \
+    -fvisibility=hidden
+ue_common_cppflags := \
+    -Wnon-virtual-dtor \
+    -fno-strict-aliasing \
+    -std=gnu++11
+ue_common_ldflags := \
+    -Wl,--gc-sections
+ue_common_c_includes := \
+    $(LOCAL_PATH)/client_library/include \
+    external/gtest/include \
+    system
+ue_common_shared_libraries := \
+    libbrillo \
+    libbrillo-http \
+    libbrillo-stream \
+    libchrome
+
+ifeq ($(BRILLO_USE_DBUS),1)
+ue_common_shared_libraries += \
+    libbrillo-dbus \
+    libchrome-dbus
+endif  # BRILLO_USE_DBUS == 1
+
+
+ifeq ($(BRILLO_USE_DBUS),1)
+
+# update_engine_client-dbus-proxies (from generate-dbus-proxies.gypi)
+# ========================================================
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_engine_client-dbus-proxies
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_SRC_FILES := \
+    dbus_bindings/dbus-service-config.json \
+    dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml
+LOCAL_DBUS_PROXY_PREFIX := update_engine
+include $(BUILD_STATIC_LIBRARY)
+
+endif  # BRILLO_USE_DBUS == 1
+
+# update_metadata-protos (type: static_library)
+# ========================================================
+# Protobufs.
+ue_update_metadata_protos_exported_static_libraries := \
+    update_metadata-protos
+ue_update_metadata_protos_exported_shared_libraries := \
+    libprotobuf-cpp-lite-rtti
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_metadata-protos
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+generated_sources_dir := $(call local-generated-sources-dir)
+LOCAL_EXPORT_C_INCLUDE_DIRS := $(generated_sources_dir)/proto/system
+LOCAL_SRC_FILES := \
+    update_metadata.proto
+include $(BUILD_STATIC_LIBRARY)
+
+ifeq ($(BRILLO_USE_DBUS),1)
+
+# update_engine-dbus-adaptor (from generate-dbus-adaptors.gypi)
+# ========================================================
+# Chrome D-Bus bindings.
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_engine-dbus-adaptor
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_SRC_FILES := \
+    dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml
+include $(BUILD_STATIC_LIBRARY)
+
+# update_engine-dbus-libcros-client (from generate-dbus-proxies.gypi)
+# ========================================================
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_engine-dbus-libcros-client
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_SRC_FILES := \
+    dbus_bindings/org.chromium.LibCrosService.dbus-xml
+LOCAL_DBUS_PROXY_PREFIX := libcros
+include $(BUILD_STATIC_LIBRARY)
+
+endif  # BRILLO_USE_DBUS == 1
+
+# libpayload_consumer (type: static_library)
+# ========================================================
+# The payload application component and common dependencies.
+ue_libpayload_consumer_exported_static_libraries := \
+    update_metadata-protos \
+    libxz \
+    libbz \
+    $(ue_update_metadata_protos_exported_static_libraries)
+ue_libpayload_consumer_exported_shared_libraries := \
+    libcrypto \
+    libcurl \
+    libssl \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := libpayload_consumer
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CLANG := true
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := \
+    $(ue_common_c_includes) \
+    external/e2fsprogs/lib
+LOCAL_STATIC_LIBRARIES := \
+    update_metadata-protos \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_update_metadata_protos_exported_static_libraries)
+LOCAL_SHARED_LIBRARIES := \
+    $(ue_common_shared_libraries) \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+LOCAL_SRC_FILES := \
+    common/action_processor.cc \
+    common/boot_control_stub.cc \
+    common/certificate_checker.cc \
+    common/clock.cc \
+    common/constants.cc \
+    common/hash_calculator.cc \
+    common/http_common.cc \
+    common/http_fetcher.cc \
+    common/hwid_override.cc \
+    common/libcurl_http_fetcher.cc \
+    common/multi_range_http_fetcher.cc \
+    common/platform_constants_android.cc \
+    common/prefs.cc \
+    common/subprocess.cc \
+    common/terminator.cc \
+    common/utils.cc \
+    payload_consumer/bzip_extent_writer.cc \
+    payload_consumer/delta_performer.cc \
+    payload_consumer/download_action.cc \
+    payload_consumer/extent_writer.cc \
+    payload_consumer/file_descriptor.cc \
+    payload_consumer/file_writer.cc \
+    payload_consumer/filesystem_verifier_action.cc \
+    payload_consumer/install_plan.cc \
+    payload_consumer/payload_constants.cc \
+    payload_consumer/payload_verifier.cc \
+    payload_consumer/postinstall_runner_action.cc \
+    payload_consumer/xz_extent_writer.cc
+include $(BUILD_STATIC_LIBRARY)
+
+ifeq ($(BRILLO_USE_DBUS),1)
+
+# libupdate_engine (type: static_library)
+# ========================================================
+# The main daemon static_library with all the code used to check for updates
+# with Omaha and expose a DBus daemon.
+ue_libupdate_engine_exported_c_includes := \
+    $(LOCAL_PATH)/include \
+    external/cros/system_api/dbus
+ue_libupdate_engine_exported_static_libraries := \
+    libpayload_consumer \
+    update_metadata-protos \
+    update_engine-dbus-adaptor \
+    update_engine-dbus-libcros-client \
+    update_engine_client-dbus-proxies \
+    libbz \
+    libfs_mgr \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_update_metadata_protos_exported_static_libraries)
+ue_libupdate_engine_exported_shared_libraries := \
+    libdbus \
+    libmetrics \
+    libshill-client \
+    libexpat \
+    libbrillo-policy \
+    libhardware \
+    libcutils \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := libupdate_engine
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CLANG := true
+LOCAL_EXPORT_C_INCLUDE_DIRS := $(ue_libupdate_engine_exported_c_includes)
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := \
+    $(ue_common_c_includes) \
+    $(ue_libupdate_engine_exported_c_includes)
+LOCAL_STATIC_LIBRARIES := \
+    libpayload_consumer \
+    update_metadata-protos \
+    update_engine-dbus-adaptor \
+    update_engine-dbus-libcros-client \
+    update_engine_client-dbus-proxies \
+    $(ue_libupdate_engine_exported_static_libraries) \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_update_metadata_protos_exported_static_libraries)
+LOCAL_SHARED_LIBRARIES := \
+    $(ue_common_shared_libraries) \
+    $(ue_libupdate_engine_exported_shared_libraries) \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+LOCAL_SRC_FILES := \
+    boot_control_android.cc \
+    chrome_browser_proxy_resolver.cc \
+    connection_manager.cc \
+    daemon.cc \
+    dbus_service.cc \
+    hardware_android.cc \
+    image_properties_android.cc \
+    libcros_proxy.cc \
+    metrics.cc \
+    metrics_utils.cc \
+    omaha_request_action.cc \
+    omaha_request_params.cc \
+    omaha_response_handler_action.cc \
+    p2p_manager.cc \
+    payload_state.cc \
+    proxy_resolver.cc \
+    real_system_state.cc \
+    shill_proxy.cc \
+    update_attempter.cc \
+    update_manager/boxed_value.cc \
+    update_manager/chromeos_policy.cc \
+    update_manager/default_policy.cc \
+    update_manager/evaluation_context.cc \
+    update_manager/policy.cc \
+    update_manager/real_config_provider.cc \
+    update_manager/real_device_policy_provider.cc \
+    update_manager/real_random_provider.cc \
+    update_manager/real_shill_provider.cc \
+    update_manager/real_system_provider.cc \
+    update_manager/real_time_provider.cc \
+    update_manager/real_updater_provider.cc \
+    update_manager/state_factory.cc \
+    update_manager/update_manager.cc \
+    update_status_utils.cc
+include $(BUILD_STATIC_LIBRARY)
+
+endif  # BRILLO_USE_DBUS == 1
+
+# update_engine (type: executable)
+# ========================================================
+# update_engine daemon.
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_engine
+LOCAL_MODULE_CLASS := EXECUTABLES
+LOCAL_REQUIRED_MODULES := \
+    bspatch \
+    cacerts_google
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_CLANG := true
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := \
+    $(ue_common_c_includes)
+
+ifdef BRILLO
+
+LOCAL_C_INCLUDES += \
+    $(ue_libupdate_engine_exported_c_includes)
+LOCAL_STATIC_LIBRARIES := \
+    libupdate_engine \
+    $(ue_libupdate_engine_exported_static_libraries)
+
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_SHARED_LIBRARIES := \
+    $(ue_common_shared_libraries) \
+    $(ue_libupdate_engine_exported_shared_libraries)
+LOCAL_SRC_FILES := \
+    main.cc
+
+else  # !defined(BRILLO)
+
+LOCAL_AIDL_INCLUDES := $(LOCAL_PATH)/binder_bindings
+LOCAL_SHARED_LIBRARIES := \
+    libbinder \
+    liblog \
+    libutils
+LOCAL_SRC_FILES := \
+    binder_bindings/android/os/IUpdateEngine.aidl \
+    binder_bindings/android/os/IUpdateEnginePayloadApplicationCallback.aidl \
+    binder_main.cc \
+    binder_service.cc
+
+endif  # defined(BRILLO)
+
+LOCAL_INIT_RC := update_engine.rc
+include $(BUILD_EXECUTABLE)
+
+ifeq ($(BRILLO_USE_DBUS),1)
+
+# update_engine_client (type: executable)
+# ========================================================
+# update_engine console client.
+include $(CLEAR_VARS)
+LOCAL_MODULE := update_engine_client
+LOCAL_MODULE_CLASS := EXECUTABLES
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CLANG := true
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := \
+    $(ue_common_c_includes) \
+    $(LOCAL_PATH)/include
+LOCAL_STATIC_LIBRARIES := update_engine_client-dbus-proxies
+LOCAL_SHARED_LIBRARIES := $(ue_common_shared_libraries)
+LOCAL_SRC_FILES := \
+    update_engine_client.cc
+include $(BUILD_EXECUTABLE)
+
+endif  # BRILLO_USE_DBUS == 1
+
+# libpayload_generator (type: static_library)
+# ========================================================
+# server-side code. This is used for delta_generator and unittests but not
+# for any client code.
+ue_libpayload_generator_exported_static_libraries := \
+    libpayload_consumer \
+    update_metadata-protos \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_update_metadata_protos_exported_static_libraries)
+ue_libpayload_generator_exported_shared_libraries := \
+    libext2fs \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := libpayload_generator
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CLANG := true
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := $(ue_common_c_includes)
+LOCAL_STATIC_LIBRARIES := \
+    libpayload_consumer \
+    update_metadata-protos \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_update_metadata_protos_exported_static_libraries)
+LOCAL_SHARED_LIBRARIES := \
+    $(ue_common_shared_libraries) \
+    $(ue_libpayload_generator_exported_shared_libraries) \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_update_metadata_protos_exported_shared_libraries)
+LOCAL_SRC_FILES := \
+    payload_generator/ab_generator.cc \
+    payload_generator/annotated_operation.cc \
+    payload_generator/blob_file_writer.cc \
+    payload_generator/block_mapping.cc \
+    payload_generator/bzip.cc \
+    payload_generator/cycle_breaker.cc \
+    payload_generator/delta_diff_generator.cc \
+    payload_generator/delta_diff_utils.cc \
+    payload_generator/ext2_filesystem.cc \
+    payload_generator/extent_ranges.cc \
+    payload_generator/extent_utils.cc \
+    payload_generator/full_update_generator.cc \
+    payload_generator/graph_types.cc \
+    payload_generator/graph_utils.cc \
+    payload_generator/inplace_generator.cc \
+    payload_generator/payload_file.cc \
+    payload_generator/payload_generation_config.cc \
+    payload_generator/payload_signer.cc \
+    payload_generator/raw_filesystem.cc \
+    payload_generator/tarjan.cc \
+    payload_generator/topological_sort.cc
+include $(BUILD_STATIC_LIBRARY)
+
+# delta_generator (type: executable)
+# ========================================================
+# server-side delta generator.
+include $(CLEAR_VARS)
+LOCAL_MODULE := delta_generator
+LOCAL_MODULE_CLASS := EXECUTABLES
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CLANG := true
+LOCAL_CFLAGS := $(ue_common_cflags)
+LOCAL_CPPFLAGS := $(ue_common_cppflags)
+LOCAL_LDFLAGS := $(ue_common_ldflags)
+LOCAL_C_INCLUDES := $(ue_common_c_includes)
+LOCAL_STATIC_LIBRARIES := \
+    libpayload_consumer \
+    libpayload_generator \
+    $(ue_libpayload_consumer_exported_static_libraries) \
+    $(ue_libpayload_generator_exported_static_libraries)
+LOCAL_SHARED_LIBRARIES := \
+    $(ue_common_shared_libraries) \
+    $(ue_libpayload_consumer_exported_shared_libraries) \
+    $(ue_libpayload_generator_exported_shared_libraries)
+LOCAL_SRC_FILES := \
+    payload_generator/generate_delta_main.cc
+include $(BUILD_EXECUTABLE)
+
+ifeq ($(BRILLO_USE_DBUS),1)
+
+# libupdate_engine_client
+# ========================================================
+include $(CLEAR_VARS)
+LOCAL_MODULE := libupdate_engine_client
+LOCAL_RTTI_FLAG := -frtti
+LOCAL_CFLAGS := \
+    -Wall \
+    -Werror \
+    -Wno-unused-parameter
+LOCAL_CLANG := true
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_C_INCLUDES := \
+    $(LOCAL_PATH)/client_library/include \
+    external/cros/system_api/dbus \
+    system \
+    external/gtest/include
+LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/client_library/include
+LOCAL_SHARED_LIBRARIES := \
+    libchrome \
+    libchrome-dbus \
+    libbrillo \
+    libbrillo-dbus
+LOCAL_STATIC_LIBRARIES := \
+    update_engine_client-dbus-proxies
+LOCAL_SRC_FILES := \
+    client_library/client.cc \
+    client_library/client_impl.cc \
+    update_status_utils.cc
+include $(BUILD_SHARED_LIBRARY)
+
+endif  # BRILLO_USE_DBUS == 1
+
+# Update payload signing public key.
+# ========================================================
+include $(CLEAR_VARS)
+LOCAL_MODULE := brillo-update-payload-key
+LOCAL_MODULE_CLASS := ETC
+LOCAL_MODULE_PATH := $(TARGET_OUT_ETC)/update_engine
+LOCAL_MODULE_STEM := update-payload-key.pub.pem
+LOCAL_SRC_FILES := update_payload_key/brillo-update-payload-key.pub.pem
+LOCAL_BUILT_MODULE_STEM := update_payload_key/brillo-update-payload-key.pub.pem
+include $(BUILD_PREBUILT)
diff --git a/MODULE_LICENSE_APACHE2 b/MODULE_LICENSE_APACHE2
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/MODULE_LICENSE_APACHE2
diff --git a/NOTICE b/NOTICE
new file mode 100644
index 0000000..d645695
--- /dev/null
+++ b/NOTICE
@@ -0,0 +1,202 @@
+
+                                 Apache License
+                           Version 2.0, January 2004
+                        http://www.apache.org/licenses/
+
+   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+   1. Definitions.
+
+      "License" shall mean the terms and conditions for use, reproduction,
+      and distribution as defined by Sections 1 through 9 of this document.
+
+      "Licensor" shall mean the copyright owner or entity authorized by
+      the copyright owner that is granting the License.
+
+      "Legal Entity" shall mean the union of the acting entity and all
+      other entities that control, are controlled by, or are under common
+      control with that entity. For the purposes of this definition,
+      "control" means (i) the power, direct or indirect, to cause the
+      direction or management of such entity, whether by contract or
+      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+      outstanding shares, or (iii) beneficial ownership of such entity.
+
+      "You" (or "Your") shall mean an individual or Legal Entity
+      exercising permissions granted by this License.
+
+      "Source" form shall mean the preferred form for making modifications,
+      including but not limited to software source code, documentation
+      source, and configuration files.
+
+      "Object" form shall mean any form resulting from mechanical
+      transformation or translation of a Source form, including but
+      not limited to compiled object code, generated documentation,
+      and conversions to other media types.
+
+      "Work" shall mean the work of authorship, whether in Source or
+      Object form, made available under the License, as indicated by a
+      copyright notice that is included in or attached to the work
+      (an example is provided in the Appendix below).
+
+      "Derivative Works" shall mean any work, whether in Source or Object
+      form, that is based on (or derived from) the Work and for which the
+      editorial revisions, annotations, elaborations, or other modifications
+      represent, as a whole, an original work of authorship. For the purposes
+      of this License, Derivative Works shall not include works that remain
+      separable from, or merely link (or bind by name) to the interfaces of,
+      the Work and Derivative Works thereof.
+
+      "Contribution" shall mean any work of authorship, including
+      the original version of the Work and any modifications or additions
+      to that Work or Derivative Works thereof, that is intentionally
+      submitted to Licensor for inclusion in the Work by the copyright owner
+      or by an individual or Legal Entity authorized to submit on behalf of
+      the copyright owner. For the purposes of this definition, "submitted"
+      means any form of electronic, verbal, or written communication sent
+      to the Licensor or its representatives, including but not limited to
+      communication on electronic mailing lists, source code control systems,
+      and issue tracking systems that are managed by, or on behalf of, the
+      Licensor for the purpose of discussing and improving the Work, but
+      excluding communication that is conspicuously marked or otherwise
+      designated in writing by the copyright owner as "Not a Contribution."
+
+      "Contributor" shall mean Licensor and any individual or Legal Entity
+      on behalf of whom a Contribution has been received by Licensor and
+      subsequently incorporated within the Work.
+
+   2. Grant of Copyright License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      copyright license to reproduce, prepare Derivative Works of,
+      publicly display, publicly perform, sublicense, and distribute the
+      Work and such Derivative Works in Source or Object form.
+
+   3. Grant of Patent License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      (except as stated in this section) patent license to make, have made,
+      use, offer to sell, sell, import, and otherwise transfer the Work,
+      where such license applies only to those patent claims licensable
+      by such Contributor that are necessarily infringed by their
+      Contribution(s) alone or by combination of their Contribution(s)
+      with the Work to which such Contribution(s) was submitted. If You
+      institute patent litigation against any entity (including a
+      cross-claim or counterclaim in a lawsuit) alleging that the Work
+      or a Contribution incorporated within the Work constitutes direct
+      or contributory patent infringement, then any patent licenses
+      granted to You under this License for that Work shall terminate
+      as of the date such litigation is filed.
+
+   4. Redistribution. You may reproduce and distribute copies of the
+      Work or Derivative Works thereof in any medium, with or without
+      modifications, and in Source or Object form, provided that You
+      meet the following conditions:
+
+      (a) You must give any other recipients of the Work or
+          Derivative Works a copy of this License; and
+
+      (b) You must cause any modified files to carry prominent notices
+          stating that You changed the files; and
+
+      (c) You must retain, in the Source form of any Derivative Works
+          that You distribute, all copyright, patent, trademark, and
+          attribution notices from the Source form of the Work,
+          excluding those notices that do not pertain to any part of
+          the Derivative Works; and
+
+      (d) If the Work includes a "NOTICE" text file as part of its
+          distribution, then any Derivative Works that You distribute must
+          include a readable copy of the attribution notices contained
+          within such NOTICE file, excluding those notices that do not
+          pertain to any part of the Derivative Works, in at least one
+          of the following places: within a NOTICE text file distributed
+          as part of the Derivative Works; within the Source form or
+          documentation, if provided along with the Derivative Works; or,
+          within a display generated by the Derivative Works, if and
+          wherever such third-party notices normally appear. The contents
+          of the NOTICE file are for informational purposes only and
+          do not modify the License. You may add Your own attribution
+          notices within Derivative Works that You distribute, alongside
+          or as an addendum to the NOTICE text from the Work, provided
+          that such additional attribution notices cannot be construed
+          as modifying the License.
+
+      You may add Your own copyright statement to Your modifications and
+      may provide additional or different license terms and conditions
+      for use, reproduction, or distribution of Your modifications, or
+      for any such Derivative Works as a whole, provided Your use,
+      reproduction, and distribution of the Work otherwise complies with
+      the conditions stated in this License.
+
+   5. Submission of Contributions. Unless You explicitly state otherwise,
+      any Contribution intentionally submitted for inclusion in the Work
+      by You to the Licensor shall be under the terms and conditions of
+      this License, without any additional terms or conditions.
+      Notwithstanding the above, nothing herein shall supersede or modify
+      the terms of any separate license agreement you may have executed
+      with Licensor regarding such Contributions.
+
+   6. Trademarks. This License does not grant permission to use the trade
+      names, trademarks, service marks, or product names of the Licensor,
+      except as required for reasonable and customary use in describing the
+      origin of the Work and reproducing the content of the NOTICE file.
+
+   7. Disclaimer of Warranty. Unless required by applicable law or
+      agreed to in writing, Licensor provides the Work (and each
+      Contributor provides its Contributions) on an "AS IS" BASIS,
+      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+      implied, including, without limitation, any warranties or conditions
+      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+      PARTICULAR PURPOSE. You are solely responsible for determining the
+      appropriateness of using or redistributing the Work and assume any
+      risks associated with Your exercise of permissions under this License.
+
+   8. Limitation of Liability. In no event and under no legal theory,
+      whether in tort (including negligence), contract, or otherwise,
+      unless required by applicable law (such as deliberate and grossly
+      negligent acts) or agreed to in writing, shall any Contributor be
+      liable to You for damages, including any direct, indirect, special,
+      incidental, or consequential damages of any character arising as a
+      result of this License or out of the use or inability to use the
+      Work (including but not limited to damages for loss of goodwill,
+      work stoppage, computer failure or malfunction, or any and all
+      other commercial damages or losses), even if such Contributor
+      has been advised of the possibility of such damages.
+
+   9. Accepting Warranty or Additional Liability. While redistributing
+      the Work or Derivative Works thereof, You may choose to offer,
+      and charge a fee for, acceptance of support, warranty, indemnity,
+      or other liability obligations and/or rights consistent with this
+      License. However, in accepting such obligations, You may act only
+      on Your own behalf and on Your sole responsibility, not on behalf
+      of any other Contributor, and only if You agree to indemnify,
+      defend, and hold each Contributor harmless for any liability
+      incurred by, or claims asserted against, such Contributor by reason
+      of your accepting any such warranty or additional liability.
+
+   END OF TERMS AND CONDITIONS
+
+   APPENDIX: How to apply the Apache License to your work.
+
+      To apply the Apache License to your work, attach the following
+      boilerplate notice, with the fields enclosed by brackets "[]"
+      replaced with your own identifying information. (Don't include
+      the brackets!)  The text should be enclosed in the appropriate
+      comment syntax for the file format. We also recommend that a
+      file or class name and description of purpose be included on the
+      same "printed page" as the copyright notice for easier
+      identification within third-party archives.
+
+   Copyright [yyyy] [name of copyright owner]
+
+   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.
diff --git a/OWNERS b/OWNERS
new file mode 100644
index 0000000..fafbecc
--- /dev/null
+++ b/OWNERS
@@ -0,0 +1,4 @@
+set noparent
+deymo@chromium.org
+garnold@chromium.org
+zeuthen@chromium.org
diff --git a/PRESUBMIT.cfg b/PRESUBMIT.cfg
new file mode 100644
index 0000000..087dfa3
--- /dev/null
+++ b/PRESUBMIT.cfg
@@ -0,0 +1,3 @@
+[Hook Overrides]
+cros_license_check: false
+aosp_license_check: true
diff --git a/UpdateEngine.conf b/UpdateEngine.conf
new file mode 100644
index 0000000..8a91607
--- /dev/null
+++ b/UpdateEngine.conf
@@ -0,0 +1,64 @@
+<!DOCTYPE busconfig PUBLIC "-//freedesktop//DTD D-BUS Bus Configuration 1.0//EN"
+  "http://www.freedesktop.org/standards/dbus/1.0/busconfig.dtd">
+<busconfig>
+  <policy user="root">
+    <allow own="org.chromium.UpdateEngine" />
+    <allow send_destination="org.chromium.UpdateEngine" />
+  </policy>
+  <policy user="chronos">
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="AttemptUpdate"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="AttemptUpdateWithFlags"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="AttemptRollback"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="CanRollback"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetRollbackPartition"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="ResetStatus"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetStatus"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="RebootIfNeeded"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="SetChannel"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetChannel"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="SetP2PUpdatePermission"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetP2PUpdatePermission"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="SetUpdateOverCellularPermission"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetUpdateOverCellularPermission"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetDurationSinceUpdate"/>
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetPrevVersion"/>
+    <allow send_interface="org.chromium.UpdateEngineLibcrosProxyResolvedInterface" />
+  </policy>
+  <policy user="power">
+    <allow send_destination="org.chromium.UpdateEngine"
+           send_interface="org.chromium.UpdateEngineInterface"
+           send_member="GetStatus"/>
+  </policy>
+</busconfig>
diff --git a/WATCHLISTS b/WATCHLISTS
new file mode 100644
index 0000000..bcce0de
--- /dev/null
+++ b/WATCHLISTS
@@ -0,0 +1,14 @@
+# See http://dev.chromium.org/developers/contributing-code/watchlists for
+# a description of this file's format.
+# Please keep these keys in alphabetical order.
+
+{
+  'WATCHLIST_DEFINITIONS': {
+    'all': {
+      'filepath': '.',
+    },
+  },
+  'WATCHLISTS': {
+    'all': ['adlr@chromium.org', 'petkov@chromium.org']
+  },
+}
diff --git a/binder_bindings/android/os/IUpdateEngine.aidl b/binder_bindings/android/os/IUpdateEngine.aidl
new file mode 100644
index 0000000..ebc3ffb
--- /dev/null
+++ b/binder_bindings/android/os/IUpdateEngine.aidl
@@ -0,0 +1,28 @@
+/*
+ * Copyright (C) 2015 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.
+ */
+
+package android.os;
+
+import android.os.IUpdateEnginePayloadApplicationCallback;
+
+interface IUpdateEngine {
+  int applyPayload(String url,
+                   in String[] headerKeyValuePairs,
+                   IUpdateEnginePayloadApplicationCallback callback);
+  void suspend();
+  void resume();
+  void cancel();
+}
diff --git a/binder_bindings/android/os/IUpdateEnginePayloadApplicationCallback.aidl b/binder_bindings/android/os/IUpdateEnginePayloadApplicationCallback.aidl
new file mode 100644
index 0000000..871ef1d
--- /dev/null
+++ b/binder_bindings/android/os/IUpdateEnginePayloadApplicationCallback.aidl
@@ -0,0 +1,22 @@
+/*
+ * Copyright (C) 2015 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.
+ */
+
+package android.os;
+
+oneway interface IUpdateEnginePayloadApplicationCallback {
+  void onStatusUpdate(int status_code, float percentage);
+  void onPayloadApplicationComplete(int error_code);
+}
diff --git a/binder_main.cc b/binder_main.cc
new file mode 100644
index 0000000..7d5c975
--- /dev/null
+++ b/binder_main.cc
@@ -0,0 +1,91 @@
+//
+// Copyright (C) 2015 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 <binder/IPCThreadState.h>
+#include <binder/IServiceManager.h>
+#include <binder/ProcessState.h>
+#include <utils/Errors.h>
+#include <utils/Log.h>
+#include <utils/Looper.h>
+#include <utils/StrongPointer.h>
+
+#include "update_engine/binder_service.h"
+
+// Log to logcat as update_engine.
+#undef LOG_TAG
+#define LOG_TAG "update_engine"
+
+namespace android {
+namespace {
+
+class BinderCallback : public LooperCallback {
+ public:
+  BinderCallback() {}
+  ~BinderCallback() override {}
+
+  int handleEvent(int /* fd */, int /* events */, void* /* data */) override {
+    IPCThreadState::self()->handlePolledCommands();
+    return 1;  // Continue receiving callbacks.
+  }
+};
+
+bool run(const sp<IBinder>& service) {
+  sp<Looper> looper(Looper::prepare(0 /* opts */));
+
+  ALOGD("Connecting to binder driver");
+  int binder_fd = -1;
+  ProcessState::self()->setThreadPoolMaxThreadCount(0);
+  IPCThreadState::self()->disableBackgroundScheduling(true);
+  IPCThreadState::self()->setupPolling(&binder_fd);
+  if (binder_fd < 0) {
+    return false;
+  }
+
+  sp<BinderCallback> cb(new BinderCallback);
+  if (looper->addFd(binder_fd, Looper::POLL_CALLBACK, Looper::EVENT_INPUT, cb,
+                    nullptr) != 1) {
+    ALOGE("Failed to add binder FD to Looper");
+    return false;
+  }
+
+  ALOGD("Registering update_engine with the service manager");
+  status_t status = defaultServiceManager()->addService(
+      service->getInterfaceDescriptor(), service);
+  if (status != android::OK) {
+    ALOGE("Failed to register update_engine with the service manager.");
+    return false;
+  }
+
+  ALOGD("Entering update_engine mainloop");
+  while (true) {
+    const int result = looper->pollAll(-1 /* timeoutMillis */);
+    ALOGD("Looper returned %d", result);
+  }
+  // We should never get here.
+  return false;
+}
+
+}  // namespace
+}  // namespace android
+
+int main(int argc, char** argv) {
+  android::sp<android::IBinder> service(
+      new chromeos_update_engine::BinderService);
+  if (!android::run(service)) {
+    return 1;
+  }
+  return 0;
+}
diff --git a/binder_service.cc b/binder_service.cc
new file mode 100644
index 0000000..8029505
--- /dev/null
+++ b/binder_service.cc
@@ -0,0 +1,49 @@
+//
+// Copyright (C) 2015 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 "update_engine/binder_service.h"
+
+using android::OK;
+using android::String16;
+using android::os::IUpdateEnginePayloadApplicationCallback;
+using android::sp;
+using android::binder::Status;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+Status BinderService::applyPayload(
+    const String16& url,
+    const vector<String16>& header_kv_pairs,
+    const sp<IUpdateEnginePayloadApplicationCallback>& callback,
+    int32_t* return_value) {
+  *return_value = 0;
+  return Status::ok();
+}
+
+Status BinderService::suspend() {
+  return Status::ok();
+}
+
+Status BinderService::resume() {
+  return Status::ok();
+}
+
+Status BinderService::cancel() {
+  return Status::ok();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/binder_service.h b/binder_service.h
new file mode 100644
index 0000000..bbbe5b6
--- /dev/null
+++ b/binder_service.h
@@ -0,0 +1,52 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_BINDER_SERVICE_H_
+#define UPDATE_ENGINE_BINDER_SERVICE_H_
+
+#include <vector>
+
+#include <utils/Errors.h>
+#include <utils/String16.h>
+#include <utils/StrongPointer.h>
+
+#include "android/os/BnUpdateEngine.h"
+#include "android/os/IUpdateEnginePayloadApplicationCallback.h"
+
+namespace chromeos_update_engine {
+
+class BinderService : public android::os::BnUpdateEngine {
+ public:
+  BinderService() = default;
+  virtual ~BinderService() = default;
+
+  android::binder::Status applyPayload(
+      const android::String16& url,
+      const std::vector<android::String16>& header_kv_pairs,
+      const android::sp<android::os::IUpdateEnginePayloadApplicationCallback>&
+          callback,
+      int32_t* return_value) override;
+
+  android::binder::Status suspend() override;
+
+  android::binder::Status resume() override;
+
+  android::binder::Status cancel() override;
+};  // class BinderService
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_BINDER_SERVICE_H_
diff --git a/boot_control_android.cc b/boot_control_android.cc
new file mode 100644
index 0000000..275d2aa
--- /dev/null
+++ b/boot_control_android.cc
@@ -0,0 +1,200 @@
+//
+// Copyright (C) 2015 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 "update_engine/boot_control_android.h"
+
+#include <base/bind.h>
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/message_loop.h>
+#include <cutils/properties.h>
+#include <fs_mgr.h>
+
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace {
+
+// Open the appropriate fstab file and fallback to /fstab.device if
+// that's what's being used.
+static struct fstab* OpenFSTab() {
+  char propbuf[PROPERTY_VALUE_MAX];
+  struct fstab* fstab;
+
+  property_get("ro.hardware", propbuf, "");
+  string fstab_name = string("/fstab.") + propbuf;
+  fstab = fs_mgr_read_fstab(fstab_name.c_str());
+  if (fstab != nullptr)
+    return fstab;
+
+  fstab = fs_mgr_read_fstab("/fstab.device");
+  return fstab;
+}
+
+}  // namespace
+
+
+namespace chromeos_update_engine {
+
+namespace boot_control {
+
+// Factory defined in boot_control.h.
+std::unique_ptr<BootControlInterface> CreateBootControl() {
+  std::unique_ptr<BootControlAndroid> boot_control(new BootControlAndroid());
+  if (!boot_control->Init()) {
+    return nullptr;
+  }
+  return brillo::make_unique_ptr(boot_control.release());
+}
+
+}  // namespace boot_control
+
+bool BootControlAndroid::Init() {
+  const hw_module_t* hw_module;
+  int ret;
+
+  ret = hw_get_module(BOOT_CONTROL_HARDWARE_MODULE_ID, &hw_module);
+  if (ret != 0) {
+    LOG(ERROR) << "Error loading boot_control HAL implementation.";
+    return false;
+  }
+
+  module_ = reinterpret_cast<boot_control_module_t*>(const_cast<hw_module_t*>(hw_module));
+  module_->init(module_);
+
+  LOG(INFO) << "Loaded boot_control HAL "
+            << "'" << hw_module->name << "' "
+            << "version " << (hw_module->module_api_version>>8) << "."
+            << (hw_module->module_api_version&0xff) << " "
+            << "authored by '" << hw_module->author << "'.";
+  return true;
+}
+
+unsigned int BootControlAndroid::GetNumSlots() const {
+  return module_->getNumberSlots(module_);
+}
+
+BootControlInterface::Slot BootControlAndroid::GetCurrentSlot() const {
+  return module_->getCurrentSlot(module_);
+}
+
+bool BootControlAndroid::GetPartitionDevice(const string& partition_name,
+                                            Slot slot,
+                                            string* device) const {
+  struct fstab* fstab;
+  struct fstab_rec* record;
+
+  // We can't use fs_mgr to look up |partition_name| because fstab
+  // doesn't list every slot partition (it uses the slotselect option
+  // to mask the suffix).
+  //
+  // We can however assume that there's an entry for the /misc mount
+  // point and use that to get the device file for the misc
+  // partition. This helps us locate the disk that |partition_name|
+  // resides on. From there we'll assume that a by-name scheme is used
+  // so we can just replace the trailing "misc" by the given
+  // |partition_name| and suffix corresponding to |slot|, e.g.
+  //
+  //   /dev/block/platform/soc.0/7824900.sdhci/by-name/misc ->
+  //   /dev/block/platform/soc.0/7824900.sdhci/by-name/boot_a
+  //
+  // If needed, it's possible to relax the by-name assumption in the
+  // future by trawling /sys/block looking for the appropriate sibling
+  // of misc and then finding an entry in /dev matching the sysfs
+  // entry.
+
+  fstab = OpenFSTab();
+  if (fstab == nullptr) {
+    LOG(ERROR) << "Error opening fstab file.";
+    return false;
+  }
+  record = fs_mgr_get_entry_for_mount_point(fstab, "/misc");
+  if (record == nullptr) {
+    LOG(ERROR) << "Error finding /misc entry in fstab file.";
+    fs_mgr_free_fstab(fstab);
+    return false;
+  }
+
+  base::FilePath misc_device = base::FilePath(record->blk_device);
+  fs_mgr_free_fstab(fstab);
+
+  if (misc_device.BaseName() != base::FilePath("misc")) {
+    LOG(ERROR) << "Device file " << misc_device.value() << " for /misc "
+               << "is not in the expected format.";
+    return false;
+  }
+
+  const char* suffix = module_->getSuffix(module_, slot);
+  if (suffix == nullptr) {
+    LOG(ERROR) << "boot_control impl returned no suffix for slot "
+               << SlotName(slot);
+    return false;
+  }
+
+  base::FilePath path = misc_device.DirName().Append(partition_name + suffix);
+  if (!base::PathExists(path)) {
+    LOG(ERROR) << "Device file " << path.value() << " does not exist.";
+    return false;
+  }
+
+  *device = path.value();
+  return true;
+}
+
+bool BootControlAndroid::IsSlotBootable(Slot slot) const {
+  int ret = module_->isSlotBootable(module_, slot);
+  if (ret < 0) {
+    LOG(ERROR) << "Unable to determine if slot " << SlotName(slot)
+               << " is bootable: " << strerror(-ret);
+    return false;
+  }
+  return ret == 1;
+}
+
+bool BootControlAndroid::MarkSlotUnbootable(Slot slot) {
+  int ret = module_->setSlotAsUnbootable(module_, slot);
+  if (ret < 0) {
+    LOG(ERROR) << "Unable to mark slot " << SlotName(slot)
+               << " as bootable: " << strerror(-ret);
+    return false;
+  }
+  return ret == 0;
+}
+
+bool BootControlAndroid::SetActiveBootSlot(Slot slot) {
+  int ret = module_->setActiveBootSlot(module_, slot);
+  if (ret < 0) {
+    LOG(ERROR) << "Unable to set the active slot to slot " << SlotName(slot)
+               << ": " << strerror(-ret);
+  }
+  return ret == 0;
+}
+
+bool BootControlAndroid::MarkBootSuccessfulAsync(
+    base::Callback<void(bool)> callback) {
+  int ret = module_->markBootSuccessful(module_);
+  if (ret < 0) {
+    LOG(ERROR) << "Unable to mark boot successful: " << strerror(-ret);
+  }
+  return brillo::MessageLoop::current()->PostTask(
+             FROM_HERE, base::Bind(callback, ret == 0)) !=
+         brillo::MessageLoop::kTaskIdNull;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/boot_control_android.h b/boot_control_android.h
new file mode 100644
index 0000000..a5a6255
--- /dev/null
+++ b/boot_control_android.h
@@ -0,0 +1,61 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_BOOT_CONTROL_ANDROID_H_
+#define UPDATE_ENGINE_BOOT_CONTROL_ANDROID_H_
+
+#include <string>
+
+#include <hardware/boot_control.h>
+#include <hardware/hardware.h>
+
+#include "update_engine/common/boot_control.h"
+
+namespace chromeos_update_engine {
+
+// The Android implementation of the BootControlInterface. This implementation
+// uses the libhardware's boot_control HAL to access the bootloader.
+class BootControlAndroid : public BootControlInterface {
+ public:
+  BootControlAndroid() = default;
+  ~BootControlAndroid() = default;
+
+  // Load boot_control HAL implementation using libhardware and
+  // initializes it. Returns false if an error occurred.
+  bool Init();
+
+  // BootControlInterface overrides.
+  unsigned int GetNumSlots() const override;
+  BootControlInterface::Slot GetCurrentSlot() const override;
+  bool GetPartitionDevice(const std::string& partition_name,
+                          BootControlInterface::Slot slot,
+                          std::string* device) const override;
+  bool IsSlotBootable(BootControlInterface::Slot slot) const override;
+  bool MarkSlotUnbootable(BootControlInterface::Slot slot) override;
+  bool SetActiveBootSlot(BootControlInterface::Slot slot) override;
+  bool MarkBootSuccessfulAsync(base::Callback<void(bool)> callback) override;
+
+ private:
+  // NOTE: There is no way to release/unload HAL implementations so
+  // this is essentially leaked on object destruction.
+  boot_control_module_t* module_;
+
+  DISALLOW_COPY_AND_ASSIGN(BootControlAndroid);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_BOOT_CONTROL_ANDROID_H_
diff --git a/boot_control_chromeos.cc b/boot_control_chromeos.cc
new file mode 100644
index 0000000..fd248ab
--- /dev/null
+++ b/boot_control_chromeos.cc
@@ -0,0 +1,304 @@
+//
+// Copyright (C) 2015 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 "update_engine/boot_control_chromeos.h"
+
+#include <string>
+
+#include <base/bind.h>
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/strings/string_util.h>
+#include <brillo/make_unique_ptr.h>
+#include <rootdev/rootdev.h>
+
+extern "C" {
+#include <vboot/vboot_host.h>
+}
+
+#include "update_engine/common/boot_control.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace {
+
+const char* kChromeOSPartitionNameKernel = "kernel";
+const char* kChromeOSPartitionNameRoot = "root";
+const char* kAndroidPartitionNameKernel = "boot";
+const char* kAndroidPartitionNameRoot = "system";
+
+// Returns the currently booted rootfs partition. "/dev/sda3", for example.
+string GetBootDevice() {
+  char boot_path[PATH_MAX];
+  // Resolve the boot device path fully, including dereferencing through
+  // dm-verity.
+  int ret = rootdev(boot_path, sizeof(boot_path), true, false);
+  if (ret < 0) {
+    LOG(ERROR) << "rootdev failed to find the root device";
+    return "";
+  }
+  LOG_IF(WARNING, ret > 0) << "rootdev found a device name with no device node";
+
+  // This local variable is used to construct the return string and is not
+  // passed around after use.
+  return boot_path;
+}
+
+// ExecCallback called when the execution of setgoodkernel finishes. Notifies
+// the caller of MarkBootSuccessfullAsync() by calling |callback| with the
+// result.
+void OnMarkBootSuccessfulDone(base::Callback<void(bool)> callback,
+                              int return_code,
+                              const string& output) {
+  callback.Run(return_code == 0);
+}
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+namespace boot_control {
+
+// Factory defined in boot_control.h.
+std::unique_ptr<BootControlInterface> CreateBootControl() {
+  std::unique_ptr<BootControlChromeOS> boot_control_chromeos(
+      new BootControlChromeOS());
+  if (!boot_control_chromeos->Init()) {
+    LOG(ERROR) << "Ignoring BootControlChromeOS failure. We won't run updates.";
+  }
+  return brillo::make_unique_ptr(boot_control_chromeos.release());
+}
+
+}  // namespace boot_control
+
+bool BootControlChromeOS::Init() {
+  string boot_device = GetBootDevice();
+  if (boot_device.empty())
+    return false;
+
+  int partition_num;
+  if (!utils::SplitPartitionName(boot_device, &boot_disk_name_, &partition_num))
+    return false;
+
+  // All installed Chrome OS devices have two slots. We don't update removable
+  // devices, so we will pretend we have only one slot in that case.
+  if (IsRemovableDevice(boot_disk_name_)) {
+    LOG(INFO)
+        << "Booted from a removable device, pretending we have only one slot.";
+    num_slots_ = 1;
+  } else {
+    // TODO(deymo): Look at the actual number of slots reported in the GPT.
+    num_slots_ = 2;
+  }
+
+  // Search through the slots to see which slot has the partition_num we booted
+  // from. This should map to one of the existing slots, otherwise something is
+  // very wrong.
+  current_slot_ = 0;
+  while (current_slot_ < num_slots_ &&
+         partition_num !=
+             GetPartitionNumber(kChromeOSPartitionNameRoot, current_slot_)) {
+    current_slot_++;
+  }
+  if (current_slot_ >= num_slots_) {
+    LOG(ERROR) << "Couldn't find the slot number corresponding to the "
+                  "partition " << boot_device
+               << ", number of slots: " << num_slots_
+               << ". This device is not updateable.";
+    num_slots_ = 1;
+    current_slot_ = BootControlInterface::kInvalidSlot;
+    return false;
+  }
+
+  LOG(INFO) << "Booted from slot " << current_slot_ << " (slot "
+            << SlotName(current_slot_) << ") of " << num_slots_
+            << " slots present on disk " << boot_disk_name_;
+  return true;
+}
+
+unsigned int BootControlChromeOS::GetNumSlots() const {
+  return num_slots_;
+}
+
+BootControlInterface::Slot BootControlChromeOS::GetCurrentSlot() const {
+  return current_slot_;
+}
+
+bool BootControlChromeOS::GetPartitionDevice(const string& partition_name,
+                                             unsigned int slot,
+                                             string* device) const {
+  int partition_num = GetPartitionNumber(partition_name, slot);
+  if (partition_num < 0)
+    return false;
+
+  string part_device = utils::MakePartitionName(boot_disk_name_, partition_num);
+  if (part_device.empty())
+    return false;
+
+  *device = part_device;
+  return true;
+}
+
+bool BootControlChromeOS::IsSlotBootable(Slot slot) const {
+  int partition_num = GetPartitionNumber(kChromeOSPartitionNameKernel, slot);
+  if (partition_num < 0)
+    return false;
+
+  CgptAddParams params;
+  memset(&params, '\0', sizeof(params));
+  params.drive_name = const_cast<char*>(boot_disk_name_.c_str());
+  params.partition = partition_num;
+
+  int retval = CgptGetPartitionDetails(&params);
+  if (retval != CGPT_OK)
+    return false;
+
+  return params.successful || params.tries > 0;
+}
+
+bool BootControlChromeOS::MarkSlotUnbootable(Slot slot) {
+  LOG(INFO) << "Marking slot " << SlotName(slot) << " unbootable";
+
+  if (slot == current_slot_) {
+    LOG(ERROR) << "Refusing to mark current slot as unbootable.";
+    return false;
+  }
+
+  int partition_num = GetPartitionNumber(kChromeOSPartitionNameKernel, slot);
+  if (partition_num < 0)
+    return false;
+
+  CgptAddParams params;
+  memset(&params, 0, sizeof(params));
+
+  params.drive_name = const_cast<char*>(boot_disk_name_.c_str());
+  params.partition = partition_num;
+
+  params.successful = false;
+  params.set_successful = true;
+
+  params.tries = 0;
+  params.set_tries = true;
+
+  int retval = CgptSetAttributes(&params);
+  if (retval != CGPT_OK) {
+    LOG(ERROR) << "Marking kernel unbootable failed.";
+    return false;
+  }
+
+  return true;
+}
+
+bool BootControlChromeOS::SetActiveBootSlot(Slot slot) {
+  LOG(INFO) << "Marking slot " << SlotName(slot) << " active.";
+
+  int partition_num = GetPartitionNumber(kChromeOSPartitionNameKernel, slot);
+  if (partition_num < 0)
+    return false;
+
+  CgptPrioritizeParams prio_params;
+  memset(&prio_params, 0, sizeof(prio_params));
+
+  prio_params.drive_name = const_cast<char*>(boot_disk_name_.c_str());
+  prio_params.set_partition = partition_num;
+
+  prio_params.max_priority = 0;
+
+  int retval = CgptPrioritize(&prio_params);
+  if (retval != CGPT_OK) {
+    LOG(ERROR) << "Unable to set highest priority for slot " << SlotName(slot)
+               << " (partition " << partition_num << ").";
+    return false;
+  }
+
+  CgptAddParams add_params;
+  memset(&add_params, 0, sizeof(add_params));
+
+  add_params.drive_name = const_cast<char*>(boot_disk_name_.c_str());
+  add_params.partition = partition_num;
+
+  add_params.tries = 6;
+  add_params.set_tries = true;
+
+  retval = CgptSetAttributes(&add_params);
+  if (retval != CGPT_OK) {
+    LOG(ERROR) << "Unable to set NumTriesLeft to " << add_params.tries
+               << " for slot " << SlotName(slot) << " (partition "
+               << partition_num << ").";
+    return false;
+  }
+
+  return true;
+}
+
+bool BootControlChromeOS::MarkBootSuccessfulAsync(
+    base::Callback<void(bool)> callback) {
+  return Subprocess::Get().Exec(
+             {"/usr/sbin/chromeos-setgoodkernel"},
+             base::Bind(&OnMarkBootSuccessfulDone, callback)) != 0;
+}
+
+// static
+string BootControlChromeOS::SysfsBlockDevice(const string& device) {
+  base::FilePath device_path(device);
+  if (device_path.DirName().value() != "/dev") {
+    return "";
+  }
+  return base::FilePath("/sys/block").Append(device_path.BaseName()).value();
+}
+
+// static
+bool BootControlChromeOS::IsRemovableDevice(const string& device) {
+  string sysfs_block = SysfsBlockDevice(device);
+  string removable;
+  if (sysfs_block.empty() ||
+      !base::ReadFileToString(base::FilePath(sysfs_block).Append("removable"),
+                              &removable)) {
+    return false;
+  }
+  base::TrimWhitespaceASCII(removable, base::TRIM_ALL, &removable);
+  return removable == "1";
+}
+
+int BootControlChromeOS::GetPartitionNumber(
+    const string partition_name,
+    BootControlInterface::Slot slot) const {
+  if (slot >= num_slots_) {
+    LOG(ERROR) << "Invalid slot number: " << slot << ", we only have "
+               << num_slots_ << " slot(s)";
+    return -1;
+  }
+
+  // In Chrome OS, the partition numbers are hard-coded:
+  //   KERNEL-A=2, ROOT-A=3, KERNEL-B=4, ROOT-B=4, ...
+  // To help compatibility between different we accept both lowercase and
+  // uppercase names in the ChromeOS or Brillo standard names.
+  // See http://www.chromium.org/chromium-os/chromiumos-design-docs/disk-format
+  string partition_lower = base::StringToLowerASCII(partition_name);
+  int base_part_num = 2 + 2 * slot;
+  if (partition_lower == kChromeOSPartitionNameKernel ||
+      partition_lower == kAndroidPartitionNameKernel)
+    return base_part_num + 0;
+  if (partition_lower == kChromeOSPartitionNameRoot ||
+      partition_lower == kAndroidPartitionNameRoot)
+    return base_part_num + 1;
+  LOG(ERROR) << "Unknown Chrome OS partition name \"" << partition_name << "\"";
+  return -1;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/boot_control_chromeos.h b/boot_control_chromeos.h
new file mode 100644
index 0000000..a1d57fe
--- /dev/null
+++ b/boot_control_chromeos.h
@@ -0,0 +1,85 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_BOOT_CONTROL_CHROMEOS_H_
+#define UPDATE_ENGINE_BOOT_CONTROL_CHROMEOS_H_
+
+#include <string>
+
+#include <base/callback.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/boot_control_interface.h"
+
+namespace chromeos_update_engine {
+
+// The Chrome OS implementation of the BootControlInterface. This interface
+// assumes the partition names and numbers used in Chrome OS devices.
+class BootControlChromeOS : public BootControlInterface {
+ public:
+  BootControlChromeOS() = default;
+  ~BootControlChromeOS() = default;
+
+  // Initialize the BootControl instance loading the constant values. Returns
+  // whether the operation succeeded. In case of failure, normally meaning
+  // some critical failure such as we couldn't determine the slot that we
+  // booted from, the implementation will pretend that there's only one slot and
+  // therefore A/B updates are disabled.
+  bool Init();
+
+  // BootControlInterface overrides.
+  unsigned int GetNumSlots() const override;
+  BootControlInterface::Slot GetCurrentSlot() const override;
+  bool GetPartitionDevice(const std::string& partition_name,
+                          BootControlInterface::Slot slot,
+                          std::string* device) const override;
+  bool IsSlotBootable(BootControlInterface::Slot slot) const override;
+  bool MarkSlotUnbootable(BootControlInterface::Slot slot) override;
+  bool SetActiveBootSlot(BootControlInterface::Slot slot) override;
+  bool MarkBootSuccessfulAsync(base::Callback<void(bool)> callback) override;
+
+ private:
+  friend class BootControlChromeOSTest;
+  FRIEND_TEST(BootControlChromeOSTest, SysfsBlockDeviceTest);
+  FRIEND_TEST(BootControlChromeOSTest, GetPartitionNumberTest);
+
+  // Returns the sysfs block device for a root block device. For example,
+  // SysfsBlockDevice("/dev/sda") returns "/sys/block/sda". Returns an empty
+  // string if the input device is not of the "/dev/xyz" form.
+  static std::string SysfsBlockDevice(const std::string& device);
+
+  // Returns true if the root |device| (e.g., "/dev/sdb") is known to be
+  // removable, false otherwise.
+  static bool IsRemovableDevice(const std::string& device);
+
+  // Return the hard-coded partition number used in Chrome OS for the passed
+  // |partition_name| and |slot|. In case of invalid data, returns -1.
+  int GetPartitionNumber(const std::string partition_name,
+                         BootControlInterface::Slot slot) const;
+
+  // Cached values for GetNumSlots() and GetCurrentSlot().
+  BootControlInterface::Slot num_slots_{1};
+  BootControlInterface::Slot current_slot_{BootControlInterface::kInvalidSlot};
+
+  // The block device of the disk we booted from, without the partition number.
+  std::string boot_disk_name_;
+
+  DISALLOW_COPY_AND_ASSIGN(BootControlChromeOS);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_BOOT_CONTROL_CHROMEOS_H_
diff --git a/chrome_browser_proxy_resolver.cc b/chrome_browser_proxy_resolver.cc
new file mode 100644
index 0000000..4971d74
--- /dev/null
+++ b/chrome_browser_proxy_resolver.cc
@@ -0,0 +1,194 @@
+//
+// Copyright (C) 2011 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 "update_engine/chrome_browser_proxy_resolver.h"
+
+#include <deque>
+#include <map>
+#include <string>
+#include <utility>
+
+#include <base/bind.h>
+#include <base/strings/string_tokenizer.h>
+#include <base/strings/string_util.h>
+
+#include "update_engine/common/utils.h"
+
+namespace chromeos_update_engine {
+
+using base::StringTokenizer;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using std::deque;
+using std::make_pair;
+using std::pair;
+using std::string;
+
+const char kLibCrosServiceName[] = "org.chromium.LibCrosService";
+const char kLibCrosProxyResolveName[] = "ProxyResolved";
+const char kLibCrosProxyResolveSignalInterface[] =
+    "org.chromium.UpdateEngineLibcrosProxyResolvedInterface";
+
+namespace {
+
+const int kTimeout = 5;  // seconds
+
+}  // namespace
+
+ChromeBrowserProxyResolver::ChromeBrowserProxyResolver(
+    LibCrosProxy* libcros_proxy)
+    : libcros_proxy_(libcros_proxy), timeout_(kTimeout) {}
+
+bool ChromeBrowserProxyResolver::Init() {
+  libcros_proxy_->ue_proxy_resolved_interface()
+      ->RegisterProxyResolvedSignalHandler(
+          base::Bind(&ChromeBrowserProxyResolver::OnProxyResolvedSignal,
+                     base::Unretained(this)),
+          base::Bind(&ChromeBrowserProxyResolver::OnSignalConnected,
+                     base::Unretained(this)));
+  return true;
+}
+
+ChromeBrowserProxyResolver::~ChromeBrowserProxyResolver() {
+  // Kill outstanding timers.
+  for (auto& timer : timers_) {
+    MessageLoop::current()->CancelTask(timer.second);
+    timer.second = MessageLoop::kTaskIdNull;
+  }
+}
+
+bool ChromeBrowserProxyResolver::GetProxiesForUrl(const string& url,
+                                                  ProxiesResolvedFn callback,
+                                                  void* data) {
+  int timeout = timeout_;
+  brillo::ErrorPtr error;
+  if (!libcros_proxy_->service_interface_proxy()->ResolveNetworkProxy(
+          url.c_str(),
+          kLibCrosProxyResolveSignalInterface,
+          kLibCrosProxyResolveName,
+          &error)) {
+    LOG(WARNING) << "Can't resolve the proxy. Continuing with no proxy.";
+    timeout = 0;
+  }
+
+  callbacks_.insert(make_pair(url, make_pair(callback, data)));
+  MessageLoop::TaskId timer = MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&ChromeBrowserProxyResolver::HandleTimeout,
+                 base::Unretained(this),
+                 url),
+      TimeDelta::FromSeconds(timeout));
+  timers_.insert(make_pair(url, timer));
+  return true;
+}
+
+bool ChromeBrowserProxyResolver::DeleteUrlState(
+    const string& source_url,
+    bool delete_timer,
+    pair<ProxiesResolvedFn, void*>* callback) {
+  {
+    CallbacksMap::iterator it = callbacks_.lower_bound(source_url);
+    TEST_AND_RETURN_FALSE(it != callbacks_.end());
+    TEST_AND_RETURN_FALSE(it->first == source_url);
+    if (callback)
+      *callback = it->second;
+    callbacks_.erase(it);
+  }
+  {
+    TimeoutsMap::iterator it = timers_.lower_bound(source_url);
+    TEST_AND_RETURN_FALSE(it != timers_.end());
+    TEST_AND_RETURN_FALSE(it->first == source_url);
+    if (delete_timer)
+      MessageLoop::current()->CancelTask(it->second);
+    timers_.erase(it);
+  }
+  return true;
+}
+
+void ChromeBrowserProxyResolver::OnSignalConnected(const string& interface_name,
+                                                   const string& signal_name,
+                                                   bool successful) {
+  if (!successful) {
+    LOG(ERROR) << "Couldn't connect to the signal " << interface_name << "."
+               << signal_name;
+  }
+}
+
+void ChromeBrowserProxyResolver::OnProxyResolvedSignal(
+    const string& source_url,
+    const string& proxy_info,
+    const string& error_message) {
+  pair<ProxiesResolvedFn, void*> callback;
+  TEST_AND_RETURN(DeleteUrlState(source_url, true, &callback));
+  if (!error_message.empty()) {
+    LOG(WARNING) << "ProxyResolved error: " << error_message;
+  }
+  (*callback.first)(ParseProxyString(proxy_info), callback.second);
+}
+
+void ChromeBrowserProxyResolver::HandleTimeout(string source_url) {
+  LOG(INFO) << "Timeout handler called. Seems Chrome isn't responding.";
+  pair<ProxiesResolvedFn, void*> callback;
+  TEST_AND_RETURN(DeleteUrlState(source_url, false, &callback));
+  deque<string> proxies;
+  proxies.push_back(kNoProxy);
+  (*callback.first)(proxies, callback.second);
+}
+
+deque<string> ChromeBrowserProxyResolver::ParseProxyString(
+    const string& input) {
+  deque<string> ret;
+  // Some of this code taken from
+  // http://src.chromium.org/svn/trunk/src/net/proxy/proxy_server.cc and
+  // http://src.chromium.org/svn/trunk/src/net/proxy/proxy_list.cc
+  StringTokenizer entry_tok(input, ";");
+  while (entry_tok.GetNext()) {
+    string token = entry_tok.token();
+    base::TrimWhitespaceASCII(token, base::TRIM_ALL, &token);
+
+    // Start by finding the first space (if any).
+    string::iterator space;
+    for (space = token.begin(); space != token.end(); ++space) {
+      if (IsAsciiWhitespace(*space)) {
+        break;
+      }
+    }
+
+    string scheme = string(token.begin(), space);
+    base::StringToLowerASCII(&scheme);
+    // Chrome uses "socks" to mean socks4 and "proxy" to mean http.
+    if (scheme == "socks")
+      scheme += "4";
+    else if (scheme == "proxy")
+      scheme = "http";
+    else if (scheme != "https" &&
+             scheme != "socks4" &&
+             scheme != "socks5" &&
+             scheme != "direct")
+      continue;  // Invalid proxy scheme
+
+    string host_and_port = string(space, token.end());
+    base::TrimWhitespaceASCII(host_and_port, base::TRIM_ALL, &host_and_port);
+    if (scheme != "direct" && host_and_port.empty())
+      continue;  // Must supply host/port when non-direct proxy used.
+    ret.push_back(scheme + "://" + host_and_port);
+  }
+  if (ret.empty() || *ret.rbegin() != kNoProxy)
+    ret.push_back(kNoProxy);
+  return ret;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/chrome_browser_proxy_resolver.h b/chrome_browser_proxy_resolver.h
new file mode 100644
index 0000000..84b0c28
--- /dev/null
+++ b/chrome_browser_proxy_resolver.h
@@ -0,0 +1,98 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_CHROME_BROWSER_PROXY_RESOLVER_H_
+#define UPDATE_ENGINE_CHROME_BROWSER_PROXY_RESOLVER_H_
+
+#include <deque>
+#include <map>
+#include <string>
+#include <utility>
+
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/libcros_proxy.h"
+#include "update_engine/proxy_resolver.h"
+
+namespace chromeos_update_engine {
+
+extern const char kLibCrosServiceName[];
+extern const char kLibCrosProxyResolveName[];
+extern const char kLibCrosProxyResolveSignalInterface[];
+
+class ChromeBrowserProxyResolver : public ProxyResolver {
+ public:
+  explicit ChromeBrowserProxyResolver(LibCrosProxy* libcros_proxy);
+  ~ChromeBrowserProxyResolver() override;
+
+  // Initialize the ProxyResolver using the provided DBus proxies.
+  bool Init();
+
+  bool GetProxiesForUrl(const std::string& url,
+                        ProxiesResolvedFn callback,
+                        void* data) override;
+
+ private:
+  FRIEND_TEST(ChromeBrowserProxyResolverTest, ParseTest);
+  FRIEND_TEST(ChromeBrowserProxyResolverTest, SuccessTest);
+  typedef std::multimap<std::string, std::pair<ProxiesResolvedFn, void*>>
+      CallbacksMap;
+  typedef std::multimap<std::string, brillo::MessageLoop::TaskId> TimeoutsMap;
+
+  // Called when the signal in UpdateEngineLibcrosProxyResolvedInterface is
+  // connected.
+  void OnSignalConnected(const std::string& interface_name,
+                         const std::string& signal_name,
+                         bool successful);
+
+  // Handle a reply from Chrome:
+  void OnProxyResolvedSignal(const std::string& source_url,
+                             const std::string& proxy_info,
+                             const std::string& error_message);
+
+  // Handle no reply:
+  void HandleTimeout(std::string source_url);
+
+  // Parses a string-encoded list of proxies and returns a deque
+  // of individual proxies. The last one will always be kNoProxy.
+  static std::deque<std::string> ParseProxyString(const std::string& input);
+
+  // Deletes internal state for the first instance of url in the state.
+  // If delete_timer is set, calls CancelTask on the timer id.
+  // Returns the callback in an out parameter. Returns true on success.
+  bool DeleteUrlState(const std::string& url,
+                      bool delete_timer,
+                      std::pair<ProxiesResolvedFn, void*>* callback);
+
+  // Shutdown the dbus proxy object.
+  void Shutdown();
+
+  // DBus proxies to request a HTTP proxy resolution. The request is done in the
+  // service_interface_proxy() interface and the response is received as a
+  // signal in the ue_proxy_resolved_interface().
+  LibCrosProxy* libcros_proxy_;
+
+  int timeout_;
+  TimeoutsMap timers_;
+  CallbacksMap callbacks_;
+  DISALLOW_COPY_AND_ASSIGN(ChromeBrowserProxyResolver);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_CHROME_BROWSER_PROXY_RESOLVER_H_
diff --git a/chrome_browser_proxy_resolver_unittest.cc b/chrome_browser_proxy_resolver_unittest.cc
new file mode 100644
index 0000000..7a4de3d
--- /dev/null
+++ b/chrome_browser_proxy_resolver_unittest.cc
@@ -0,0 +1,211 @@
+//
+// Copyright (C) 2011 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 "update_engine/chrome_browser_proxy_resolver.h"
+
+#include <deque>
+#include <string>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include <base/bind.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/fake_message_loop.h>
+
+#include "libcros/dbus-proxies.h"
+#include "libcros/dbus-proxy-mocks.h"
+#include "update_engine/dbus_test_utils.h"
+
+using ::testing::Return;
+using ::testing::StrEq;
+using ::testing::_;
+using brillo::MessageLoop;
+using org::chromium::LibCrosServiceInterfaceProxyMock;
+using org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxyMock;
+using std::deque;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class ChromeBrowserProxyResolverTest : public ::testing::Test {
+ protected:
+  ChromeBrowserProxyResolverTest()
+      : service_interface_mock_(new LibCrosServiceInterfaceProxyMock()),
+        ue_proxy_resolved_interface_mock_(
+            new UpdateEngineLibcrosProxyResolvedInterfaceProxyMock()),
+        libcros_proxy_(
+            brillo::make_unique_ptr(service_interface_mock_),
+            brillo::make_unique_ptr(ue_proxy_resolved_interface_mock_)) {}
+
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    // The ProxyResolved signal should be subscribed to.
+    MOCK_SIGNAL_HANDLER_EXPECT_SIGNAL_HANDLER(
+        ue_proxy_resolved_signal_,
+        *ue_proxy_resolved_interface_mock_,
+        ProxyResolved);
+
+    EXPECT_TRUE(resolver_.Init());
+    // Run the loop once to dispatch the successfully registered signal handler.
+    EXPECT_TRUE(loop_.RunOnce(false));
+  }
+
+  void TearDown() override {
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  // Send the signal to the callback passed during registration of the
+  // ProxyResolved.
+  void SendReplySignal(const string& source_url,
+                       const string& proxy_info,
+                       const string& error_message);
+
+  void RunTest(bool chrome_replies, bool chrome_alive);
+
+ private:
+  brillo::FakeMessageLoop loop_{nullptr};
+
+  // Local pointers to the mocks. The instances are owned by the
+  // |libcros_proxy_|.
+  LibCrosServiceInterfaceProxyMock* service_interface_mock_;
+  UpdateEngineLibcrosProxyResolvedInterfaceProxyMock*
+      ue_proxy_resolved_interface_mock_;
+
+  // The registered signal handler for the signal
+  // UpdateEngineLibcrosProxyResolvedInterface.ProxyResolved.
+  chromeos_update_engine::dbus_test_utils::MockSignalHandler<
+      void(const string&, const string&, const string&)>
+      ue_proxy_resolved_signal_;
+
+  LibCrosProxy libcros_proxy_;
+  ChromeBrowserProxyResolver resolver_{&libcros_proxy_};
+};
+
+
+void ChromeBrowserProxyResolverTest::SendReplySignal(
+    const string& source_url,
+    const string& proxy_info,
+    const string& error_message) {
+  ASSERT_TRUE(ue_proxy_resolved_signal_.IsHandlerRegistered());
+  ue_proxy_resolved_signal_.signal_callback().Run(
+      source_url, proxy_info, error_message);
+}
+
+namespace {
+void CheckResponseResolved(const deque<string>& proxies,
+                           void* /* pirv_data */) {
+  EXPECT_EQ(2, proxies.size());
+  EXPECT_EQ("socks5://192.168.52.83:5555", proxies[0]);
+  EXPECT_EQ(kNoProxy, proxies[1]);
+  MessageLoop::current()->BreakLoop();
+}
+
+void CheckResponseNoReply(const deque<string>& proxies, void* /* pirv_data */) {
+  EXPECT_EQ(1, proxies.size());
+  EXPECT_EQ(kNoProxy, proxies[0]);
+  MessageLoop::current()->BreakLoop();
+}
+}  // namespace
+
+// chrome_replies should be set to whether or not we fake a reply from
+// chrome. If there's no reply, the resolver should time out.
+// If chrome_alive is false, assume that sending to chrome fails.
+void ChromeBrowserProxyResolverTest::RunTest(bool chrome_replies,
+                                             bool chrome_alive) {
+  char kUrl[] = "http://example.com/blah";
+  char kProxyConfig[] = "SOCKS5 192.168.52.83:5555;DIRECT";
+
+  EXPECT_CALL(*service_interface_mock_,
+              ResolveNetworkProxy(StrEq(kUrl),
+                                  StrEq(kLibCrosProxyResolveSignalInterface),
+                                  StrEq(kLibCrosProxyResolveName),
+                                  _,
+                                  _))
+      .WillOnce(Return(chrome_alive));
+
+  ProxiesResolvedFn get_proxies_response = &CheckResponseNoReply;
+  if (chrome_replies) {
+    get_proxies_response = &CheckResponseResolved;
+    MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&ChromeBrowserProxyResolverTest::SendReplySignal,
+                   base::Unretained(this),
+                   kUrl,
+                   kProxyConfig,
+                   ""),
+        base::TimeDelta::FromSeconds(1));
+  }
+
+  EXPECT_TRUE(resolver_.GetProxiesForUrl(kUrl, get_proxies_response, nullptr));
+  MessageLoop::current()->Run();
+}
+
+
+TEST_F(ChromeBrowserProxyResolverTest, ParseTest) {
+  // Test ideas from
+  // http://src.chromium.org/svn/trunk/src/net/proxy/proxy_list_unittest.cc
+  vector<string> inputs = {
+      "PROXY foopy:10",
+      " DIRECT",  // leading space.
+      "PROXY foopy1 ; proxy foopy2;\t DIRECT",
+      "proxy foopy1 ; SOCKS foopy2",
+      "DIRECT ; proxy foopy1 ; DIRECT ; SOCKS5 foopy2;DIRECT ",
+      "DIRECT ; proxy foopy1:80; DIRECT ; DIRECT",
+      "PROXY-foopy:10",
+      "PROXY",
+      "PROXY foopy1 ; JUNK ; JUNK ; SOCKS5 foopy2 ; ;",
+      "HTTP foopy1; SOCKS5 foopy2"};
+  vector<deque<string>> outputs = {
+      {"http://foopy:10", kNoProxy},
+      {kNoProxy},
+      {"http://foopy1", "http://foopy2", kNoProxy},
+      {"http://foopy1", "socks4://foopy2", kNoProxy},
+      {kNoProxy, "http://foopy1", kNoProxy, "socks5://foopy2", kNoProxy},
+      {kNoProxy, "http://foopy1:80", kNoProxy, kNoProxy},
+      {kNoProxy},
+      {kNoProxy},
+      {"http://foopy1", "socks5://foopy2", kNoProxy},
+      {"socks5://foopy2", kNoProxy}};
+  ASSERT_EQ(inputs.size(), outputs.size());
+
+  for (size_t i = 0; i < inputs.size(); i++) {
+    deque<string> results =
+        ChromeBrowserProxyResolver::ParseProxyString(inputs[i]);
+    deque<string>& expected = outputs[i];
+    EXPECT_EQ(results.size(), expected.size()) << "i = " << i;
+    if (expected.size() != results.size())
+      continue;
+    for (size_t j = 0; j < expected.size(); j++) {
+      EXPECT_EQ(expected[j], results[j]) << "i = " << i;
+    }
+  }
+}
+
+TEST_F(ChromeBrowserProxyResolverTest, SuccessTest) {
+  RunTest(true, true);
+}
+
+TEST_F(ChromeBrowserProxyResolverTest, NoReplyTest) {
+  RunTest(false, true);
+}
+
+TEST_F(ChromeBrowserProxyResolverTest, NoChromeTest) {
+  RunTest(false, false);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/client_library/client.cc b/client_library/client.cc
new file mode 100644
index 0000000..d6e7382
--- /dev/null
+++ b/client_library/client.cc
@@ -0,0 +1,31 @@
+//
+// Copyright (C) 2015 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 "update_engine/client_library/include/update_engine/client.h"
+
+#include <memory>
+
+#include "update_engine/client_library/client_impl.h"
+
+using std::unique_ptr;
+
+namespace update_engine {
+
+std::unique_ptr<UpdateEngineClient> UpdateEngineClient::CreateInstance() {
+  return unique_ptr<UpdateEngineClient>{new internal::UpdateEngineClientImpl{}};
+}
+
+}  // namespace update_engine
diff --git a/client_library/client_impl.cc b/client_library/client_impl.cc
new file mode 100644
index 0000000..84ca184
--- /dev/null
+++ b/client_library/client_impl.cc
@@ -0,0 +1,91 @@
+//
+// Copyright (C) 2015 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 "update_engine/client_library/client_impl.h"
+
+#include <dbus/bus.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/update_status_utils.h"
+
+using chromeos_update_engine::StringToUpdateStatus;
+using dbus::Bus;
+using org::chromium::UpdateEngineInterfaceProxy;
+using std::string;
+
+namespace update_engine {
+namespace internal {
+
+UpdateEngineClientImpl::UpdateEngineClientImpl() {
+  Bus::Options options;
+  options.bus_type = Bus::SYSTEM;
+  scoped_refptr<Bus> bus{new Bus{options}};
+  proxy_.reset(new UpdateEngineInterfaceProxy{bus});
+}
+
+bool UpdateEngineClientImpl::AttemptUpdate(const string& in_app_version,
+                                           const string& in_omaha_url,
+                                           bool at_user_request) {
+  return proxy_->AttemptUpdateWithFlags(
+      in_app_version,
+      in_omaha_url,
+      (at_user_request) ? 0 : kAttemptUpdateFlagNonInteractive,
+      nullptr);
+}
+
+bool UpdateEngineClientImpl::GetStatus(int64_t* out_last_checked_time,
+                                       double* out_progress,
+                                       UpdateStatus* out_update_status,
+                                       string* out_new_version,
+                                       int64_t* out_new_size) {
+  string status_as_string;
+  const bool success = proxy_->GetStatus(
+      out_last_checked_time,
+      out_progress,
+      &status_as_string,
+      out_new_version,
+      out_new_size,
+      nullptr);
+  if (!success) {
+    return false;
+  }
+
+  return StringToUpdateStatus(status_as_string, out_update_status);
+}
+
+bool UpdateEngineClientImpl::SetTargetChannel(const string& in_target_channel) {
+  return proxy_->SetChannel(
+      in_target_channel,
+      true,
+      nullptr);
+}
+
+bool UpdateEngineClientImpl::GetTargetChannel(string* out_channel) {
+  return proxy_->GetChannel(
+      false,  // Get the target channel.
+      out_channel,
+      nullptr);
+}
+
+bool UpdateEngineClientImpl::GetChannel(string* out_channel) {
+  return proxy_->GetChannel(
+      true,  // Get the current channel.
+      out_channel,
+      nullptr);
+}
+
+}  // namespace internal
+}  // namespace update_engine
diff --git a/client_library/client_impl.h b/client_library/client_impl.h
new file mode 100644
index 0000000..e6194d2
--- /dev/null
+++ b/client_library/client_impl.h
@@ -0,0 +1,62 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_CLIENT_LIBRARY_CLIENT_IMPL_H_
+#define UPDATE_ENGINE_CLIENT_LIBRARY_CLIENT_IMPL_H_
+
+#include <cstdint>
+#include <memory>
+#include <string>
+
+#include <base/macros.h>
+
+#include "update_engine/client_library/include/update_engine/client.h"
+#include "update_engine/dbus-proxies.h"
+
+namespace update_engine {
+namespace internal {
+
+class UpdateEngineClientImpl : public UpdateEngineClient {
+ public:
+  UpdateEngineClientImpl();
+  virtual ~UpdateEngineClientImpl() = default;
+
+  bool AttemptUpdate(const std::string& app_version,
+                     const std::string& omaha_url,
+                     bool at_user_request) override;
+
+  bool GetStatus(int64_t* out_last_checked_time,
+                 double* out_progress,
+                 UpdateStatus* out_update_status,
+                 std::string* out_new_version,
+                 int64_t* out_new_size) override;
+
+  bool SetTargetChannel(const std::string& target_channel) override;
+
+  bool GetTargetChannel(std::string* out_channel) override;
+
+  bool GetChannel(std::string* out_channel) override;
+
+ private:
+  std::unique_ptr<org::chromium::UpdateEngineInterfaceProxy> proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateEngineClientImpl);
+};  // class UpdateEngineClientImpl
+
+}  // namespace internal
+}  // namespace update_engine
+
+#endif  // UPDATE_ENGINE_CLIENT_LIBRARY_CLIENT_IMPL_H_
diff --git a/client_library/include/update_engine/client.h b/client_library/include/update_engine/client.h
new file mode 100644
index 0000000..b3cef66
--- /dev/null
+++ b/client_library/include/update_engine/client.h
@@ -0,0 +1,89 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_CLIENT_H_
+#define UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_CLIENT_H_
+
+#include <cstdint>
+#include <memory>
+#include <string>
+
+#include "update_engine/update_status.h"
+
+namespace update_engine {
+
+class UpdateEngineClient {
+ public:
+  static std::unique_ptr<UpdateEngineClient> CreateInstance();
+
+  virtual ~UpdateEngineClient() = default;
+
+  // Force the update_engine to attempt an update.
+  // |app_version|
+  //     Attempt to update to this version.  An empty string indicates that
+  //     update engine should pick the most recent image on the current channel.
+  // |omaha_url|
+  //     Force update_engine to look for updates from the given server.  Passing
+  //     empty indicates update_engine should get this parameter from its
+  //     config.  Note that update_engine will ignore this parameter in
+  //     production mode to avoid pulling untrusted updates.
+  // |at_user_request|
+  //     This update was directly requested by the user.
+  virtual bool AttemptUpdate(const std::string& app_version,
+                             const std::string& omaha_url,
+                             bool at_user_request) = 0;
+
+  // Returns the current status of the Update Engine.
+  //
+  // |out_last_checked_time|
+  //     the last time the update engine checked for an update in seconds since
+  //     the epoc.
+  // |out_progress|
+  //     when downloading an update, this is calculated as
+  //     (number of bytes received) / (total bytes).
+  // |out_update_status|
+  //     See update_status.h.
+  // |out_new_version|
+  //     string version of the new system image.
+  // |out_new_size|
+  //     number of bytes in the new system image.
+  virtual bool GetStatus(int64_t* out_last_checked_time,
+                         double* out_progress,
+                         UpdateStatus* out_update_status,
+                         std::string* out_new_version,
+                         int64_t* out_new_size) = 0;
+
+  // Changes the current channel of the device to the target channel.
+  virtual bool SetTargetChannel(const std::string& target_channel) = 0;
+
+  // Get the channel the device will switch to on reboot.
+  virtual bool GetTargetChannel(std::string* out_channel) = 0;
+
+  // Get the channel the device is currently on.
+  virtual bool GetChannel(std::string* out_channel) = 0;
+
+ protected:
+  // Use CreateInstance().
+  UpdateEngineClient() = default;
+
+ private:
+  UpdateEngineClient(const UpdateEngineClient&) = delete;
+  void operator=(const UpdateEngineClient&) = delete;
+};  // class UpdateEngineClient
+
+}  // namespace update_engine
+
+#endif  // UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_CLIENT_H_
diff --git a/client_library/include/update_engine/update_status.h b/client_library/include/update_engine/update_status.h
new file mode 100644
index 0000000..3e9af5b
--- /dev/null
+++ b/client_library/include/update_engine/update_status.h
@@ -0,0 +1,37 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_UPDATE_STATUS_H_
+#define UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_UPDATE_STATUS_H_
+
+namespace update_engine {
+
+enum class UpdateStatus {
+  IDLE = 0,
+  CHECKING_FOR_UPDATE,
+  UPDATE_AVAILABLE,
+  DOWNLOADING,
+  VERIFYING,
+  FINALIZING,
+  UPDATED_NEED_REBOOT,
+  REPORTING_ERROR_EVENT,
+  ATTEMPTING_ROLLBACK,
+  DISABLED,
+};
+
+}  // namespace update_engine
+
+#endif  // UPDATE_ENGINE_CLIENT_LIBRARY_INCLUDE_UPDATE_ENGINE_UPDATE_STATUS_H_
diff --git a/common/action.h b/common/action.h
new file mode 100644
index 0000000..d8049ac
--- /dev/null
+++ b/common/action.h
@@ -0,0 +1,218 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_ACTION_H_
+#define UPDATE_ENGINE_COMMON_ACTION_H_
+
+#include <stdio.h>
+
+#include <memory>
+#include <string>
+
+#include <base/logging.h>
+#include <base/macros.h>
+
+#include "update_engine/common/action_pipe.h"
+#include "update_engine/common/action_processor.h"
+
+// The structure of these classes (Action, ActionPipe, ActionProcessor, etc.)
+// is based on the KSAction* classes from the Google Update Engine code at
+// http://code.google.com/p/update-engine/ . The author of this file sends
+// a big thanks to that team for their high quality design, implementation,
+// and documentation.
+//
+// Readers may want to consult this wiki page from the Update Engine site:
+// http://code.google.com/p/update-engine/wiki/ActionProcessor
+// Although it's referring to the Objective-C KSAction* classes, much
+// applies here as well.
+//
+// How it works:
+//
+// First off, there is only one thread and all I/O should be asynchronous.
+// A message loop blocks whenever there is no work to be done. This happens
+// where there is no CPU work to be done and no I/O ready to transfer in or
+// out. Two kinds of events can wake up the message loop: timer alarm or file
+// descriptors. If either of these happens, the message loop finds out the owner
+// of what fired and calls the appropriate code to handle it. As such, all the
+// code in the Action* classes and the code that is calls is non-blocking.
+//
+// An ActionProcessor contains a queue of Actions to perform. When
+// ActionProcessor::StartProcessing() is called, it executes the first action.
+// Each action tells the processor when it has completed, which causes the
+// Processor to execute the next action. ActionProcessor may have a delegate
+// (an object of type ActionProcessorDelegate). If it does, the delegate
+// is called to be notified of events as they happen.
+//
+// ActionPipe classes
+//
+// See action_pipe.h
+//
+// ActionTraits
+//
+// We need to use an extra class ActionTraits. ActionTraits is a simple
+// templated class that contains only two typedefs: OutputObjectType and
+// InputObjectType. Each action class also has two typedefs of the same name
+// that are of the same type. So, to get the input/output types of, e.g., the
+// DownloadAction class, we look at the type of
+// DownloadAction::InputObjectType.
+//
+// Each concrete Action class derives from Action<T>. This means that during
+// template instantiation of Action<T>, T is declared but not defined, which
+// means that T::InputObjectType (and OutputObjectType) is not defined.
+// However, the traits class is constructed in such a way that it will be
+// template instantiated first, so Action<T> *can* find the types it needs by
+// consulting ActionTraits<T>::InputObjectType (and OutputObjectType).
+// This is why the ActionTraits classes are needed.
+
+namespace chromeos_update_engine {
+
+// It is handy to have a non-templated base class of all Actions.
+class AbstractAction {
+ public:
+  AbstractAction() : processor_(nullptr) {}
+  virtual ~AbstractAction() = default;
+
+  // Begin performing the action. Since this code is asynchronous, when this
+  // method returns, it means only that the action has started, not necessarily
+  // completed. However, it's acceptable for this method to perform the
+  // action synchronously; Action authors should understand the implications
+  // of synchronously performing, though, because this is a single-threaded
+  // app, the entire process will be blocked while the action performs.
+  //
+  // When the action is complete, it must call
+  // ActionProcessor::ActionComplete(this); to notify the processor that it's
+  // done.
+  virtual void PerformAction() = 0;
+
+  // Called on ActionProcess::ActionComplete() by ActionProcessor.
+  virtual void ActionCompleted(ErrorCode code) {}
+
+  // Called by the ActionProcessor to tell this Action which processor
+  // it belongs to.
+  void SetProcessor(ActionProcessor* processor) {
+    if (processor)
+      CHECK(!processor_);
+    else
+      CHECK(processor_);
+    processor_ = processor;
+  }
+
+  // Returns true iff the action is the current action of its ActionProcessor.
+  bool IsRunning() const {
+    if (!processor_)
+      return false;
+    return processor_->current_action() == this;
+  }
+
+  // Called on asynchronous actions if canceled. Actions may implement if
+  // there's any cleanup to do. There is no need to call
+  // ActionProcessor::ActionComplete() because the processor knows this
+  // action is terminating.
+  // Only the ActionProcessor should call this.
+  virtual void TerminateProcessing() {}
+
+  // These methods are useful for debugging. TODO(adlr): consider using
+  // std::type_info for this?
+  // Type() returns a string of the Action type. I.e., for DownloadAction,
+  // Type() would return "DownloadAction".
+  virtual std::string Type() const = 0;
+
+ protected:
+  // A weak pointer to the processor that owns this Action.
+  ActionProcessor* processor_;
+};
+
+// Forward declare a couple classes we use.
+template<typename T>
+class ActionPipe;
+template<typename T>
+class ActionTraits;
+
+template<typename SubClass>
+class Action : public AbstractAction {
+ public:
+  ~Action() override {}
+
+  // Attaches an input pipe to this Action. This is optional; an Action
+  // doesn't need to have an input pipe. The input pipe must be of the type
+  // of object that this class expects.
+  // This is generally called by ActionPipe::Bond()
+  void set_in_pipe(
+      // this type is a fancy way of saying: a shared_ptr to an
+      // ActionPipe<InputObjectType>.
+      const std::shared_ptr<ActionPipe<
+          typename ActionTraits<SubClass>::InputObjectType>>& in_pipe) {
+    in_pipe_ = in_pipe;
+  }
+
+  // Attaches an output pipe to this Action. This is optional; an Action
+  // doesn't need to have an output pipe. The output pipe must be of the type
+  // of object that this class expects.
+  // This is generally called by ActionPipe::Bond()
+  void set_out_pipe(
+      // this type is a fancy way of saying: a shared_ptr to an
+      // ActionPipe<OutputObjectType>.
+      const std::shared_ptr<ActionPipe<
+          typename ActionTraits<SubClass>::OutputObjectType>>& out_pipe) {
+    out_pipe_ = out_pipe;
+  }
+
+  // Returns true iff there is an associated input pipe. If there's an input
+  // pipe, there's an input object, but it may have been constructed with the
+  // default ctor if the previous action didn't call SetOutputObject().
+  bool HasInputObject() const { return in_pipe_.get(); }
+
+  // returns a const reference to the object in the input pipe.
+  const typename ActionTraits<SubClass>::InputObjectType& GetInputObject()
+      const {
+    CHECK(HasInputObject());
+    return in_pipe_->contents();
+  }
+
+  // Returns true iff there's an output pipe.
+  bool HasOutputPipe() const {
+    return out_pipe_.get();
+  }
+
+  // Copies the object passed into the output pipe. It will be accessible to
+  // the next Action via that action's input pipe (which is the same as this
+  // Action's output pipe).
+  void SetOutputObject(
+      const typename ActionTraits<SubClass>::OutputObjectType& out_obj) {
+    CHECK(HasOutputPipe());
+    out_pipe_->set_contents(out_obj);
+  }
+
+  // Returns a reference to the object sitting in the output pipe.
+  const typename ActionTraits<SubClass>::OutputObjectType& GetOutputObject() {
+    CHECK(HasOutputPipe());
+    return out_pipe_->contents();
+  }
+
+ protected:
+  // We use a shared_ptr to the pipe. shared_ptr objects destroy what they
+  // point to when the last such shared_ptr object dies. We consider the
+  // Actions on either end of a pipe to "own" the pipe. When the last Action
+  // of the two dies, the ActionPipe will die, too.
+  std::shared_ptr<ActionPipe<typename ActionTraits<SubClass>::InputObjectType>>
+      in_pipe_;
+  std::shared_ptr<ActionPipe<typename ActionTraits<SubClass>::OutputObjectType>>
+      out_pipe_;
+};
+
+};  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_ACTION_H_
diff --git a/common/action_pipe.h b/common/action_pipe.h
new file mode 100644
index 0000000..362817d
--- /dev/null
+++ b/common/action_pipe.h
@@ -0,0 +1,101 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_ACTION_PIPE_H_
+#define UPDATE_ENGINE_COMMON_ACTION_PIPE_H_
+
+#include <stdio.h>
+
+#include <map>
+#include <memory>
+#include <string>
+
+#include <base/logging.h>
+#include <base/macros.h>
+
+// The structure of these classes (Action, ActionPipe, ActionProcessor, etc.)
+// is based on the KSAction* classes from the Google Update Engine code at
+// http://code.google.com/p/update-engine/ . The author of this file sends
+// a big thanks to that team for their high quality design, implementation,
+// and documentation.
+
+// This class serves as a temporary holding area for an object passed out
+// from one Action and into another Action. It's templated so that it may
+// contain any type of object that an Action outputs/inputs. Actions
+// cannot be bonded (i.e., connected with a pipe) if their output/input
+// object types differ (a compiler error will result).
+//
+// An ActionPipe is generally created with the Bond() method and owned by
+// the two Action objects. a shared_ptr is used so that when the last Action
+// pointing to an ActionPipe dies, the ActionPipe dies, too.
+
+namespace chromeos_update_engine {
+
+// Used by Actions an InputObjectType or OutputObjectType to specify that
+// for that type, no object is taken/given.
+class NoneType {};
+
+template<typename T>
+class Action;
+
+template<typename ObjectType>
+class ActionPipe {
+ public:
+  virtual ~ActionPipe() {}
+
+  // This should be called by an Action on its input pipe.
+  // Returns a reference to the stored object.
+  const ObjectType& contents() const { return contents_; }
+
+  // This should be called by an Action on its output pipe.
+  // Stores a copy of the passed object in this pipe.
+  void set_contents(const ObjectType& contents) { contents_ = contents; }
+
+  // Bonds two Actions together with a new ActionPipe. The ActionPipe is
+  // jointly owned by the two Actions and will be automatically destroyed
+  // when the last Action is destroyed.
+  template<typename FromAction, typename ToAction>
+  static void Bond(FromAction* from, ToAction* to) {
+    std::shared_ptr<ActionPipe<ObjectType>> pipe(new ActionPipe<ObjectType>);
+    from->set_out_pipe(pipe);
+
+    to->set_in_pipe(pipe);  // If you get an error on this line, then
+    // it most likely means that the From object's OutputObjectType is
+    // different from the To object's InputObjectType.
+  }
+
+ private:
+  ObjectType contents_;
+
+  // The ctor is private. This is because this class should construct itself
+  // via the static Bond() method.
+  ActionPipe() {}
+  DISALLOW_COPY_AND_ASSIGN(ActionPipe);
+};
+
+// Utility function
+template<typename FromAction, typename ToAction>
+void BondActions(FromAction* from, ToAction* to) {
+  // TODO(adlr): find something like this that the compiler accepts:
+  // COMPILE_ASSERT(typeof(typename FromAction::OutputObjectType) ==
+  //                typeof(typename ToAction::InputObjectType),
+  //     FromAction_OutputObjectType_doesnt_match_ToAction_InputObjectType);
+  ActionPipe<typename FromAction::OutputObjectType>::Bond(from, to);
+}
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_ACTION_PIPE_H_
diff --git a/common/action_pipe_unittest.cc b/common/action_pipe_unittest.cc
new file mode 100644
index 0000000..9bfbc83
--- /dev/null
+++ b/common/action_pipe_unittest.cc
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/action_pipe.h"
+
+#include <gtest/gtest.h>
+#include <string>
+#include "update_engine/common/action.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+using chromeos_update_engine::ActionPipe;
+
+class ActionPipeTestAction;
+
+template<>
+class ActionTraits<ActionPipeTestAction> {
+ public:
+  typedef string OutputObjectType;
+  typedef string InputObjectType;
+};
+
+// This is a simple Action class for testing.
+class ActionPipeTestAction : public Action<ActionPipeTestAction> {
+ public:
+  typedef string InputObjectType;
+  typedef string OutputObjectType;
+  ActionPipe<string>* in_pipe() { return in_pipe_.get(); }
+  ActionPipe<string>* out_pipe() { return out_pipe_.get(); }
+  void PerformAction() {}
+  string Type() const { return "ActionPipeTestAction"; }
+};
+
+class ActionPipeTest : public ::testing::Test { };
+
+// This test creates two simple Actions and sends a message via an ActionPipe
+// from one to the other.
+TEST(ActionPipeTest, SimpleTest) {
+  ActionPipeTestAction a, b;
+  BondActions(&a, &b);
+  a.out_pipe()->set_contents("foo");
+  EXPECT_EQ("foo", b.in_pipe()->contents());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/action_processor.cc b/common/action_processor.cc
new file mode 100644
index 0000000..7ccdfbd
--- /dev/null
+++ b/common/action_processor.cc
@@ -0,0 +1,100 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/action_processor.h"
+
+#include <string>
+
+#include <base/logging.h>
+
+#include "update_engine/common/action.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+ActionProcessor::ActionProcessor()
+    : current_action_(nullptr), delegate_(nullptr) {}
+
+ActionProcessor::~ActionProcessor() {
+  if (IsRunning())
+    StopProcessing();
+  for (auto action : actions_)
+    action->SetProcessor(nullptr);
+}
+
+void ActionProcessor::EnqueueAction(AbstractAction* action) {
+  actions_.push_back(action);
+  action->SetProcessor(this);
+}
+
+void ActionProcessor::StartProcessing() {
+  CHECK(!IsRunning());
+  if (!actions_.empty()) {
+    current_action_ = actions_.front();
+    LOG(INFO) << "ActionProcessor::StartProcessing: "
+              << current_action_->Type();
+    actions_.pop_front();
+    current_action_->PerformAction();
+  }
+}
+
+void ActionProcessor::StopProcessing() {
+  CHECK(IsRunning());
+  CHECK(current_action_);
+  current_action_->TerminateProcessing();
+  CHECK(current_action_);
+  current_action_->SetProcessor(nullptr);
+  LOG(INFO) << "ActionProcessor::StopProcessing: aborted "
+            << current_action_->Type();
+  current_action_ = nullptr;
+  if (delegate_)
+    delegate_->ProcessingStopped(this);
+}
+
+void ActionProcessor::ActionComplete(AbstractAction* actionptr,
+                                     ErrorCode code) {
+  CHECK_EQ(actionptr, current_action_);
+  if (delegate_)
+    delegate_->ActionCompleted(this, actionptr, code);
+  string old_type = current_action_->Type();
+  current_action_->ActionCompleted(code);
+  current_action_->SetProcessor(nullptr);
+  current_action_ = nullptr;
+  if (actions_.empty()) {
+    LOG(INFO) << "ActionProcessor::ActionComplete: finished last action of"
+                 " type " << old_type;
+  } else if (code != ErrorCode::kSuccess) {
+    LOG(INFO) << "ActionProcessor::ActionComplete: " << old_type
+              << " action failed. Aborting processing.";
+    actions_.clear();
+  }
+  if (actions_.empty()) {
+    LOG(INFO) << "ActionProcessor::ActionComplete: finished last action of"
+                 " type " << old_type;
+    if (delegate_) {
+      delegate_->ProcessingDone(this, code);
+    }
+    return;
+  }
+  current_action_ = actions_.front();
+  actions_.pop_front();
+  LOG(INFO) << "ActionProcessor::ActionComplete: finished " << old_type
+            << ", starting " << current_action_->Type();
+  current_action_->PerformAction();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/action_processor.h b/common/action_processor.h
new file mode 100644
index 0000000..d61e12d
--- /dev/null
+++ b/common/action_processor.h
@@ -0,0 +1,116 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_ACTION_PROCESSOR_H_
+#define UPDATE_ENGINE_COMMON_ACTION_PROCESSOR_H_
+
+#include <deque>
+
+#include <base/macros.h>
+
+#include "update_engine/common/error_code.h"
+
+// The structure of these classes (Action, ActionPipe, ActionProcessor, etc.)
+// is based on the KSAction* classes from the Google Update Engine code at
+// http://code.google.com/p/update-engine/ . The author of this file sends
+// a big thanks to that team for their high quality design, implementation,
+// and documentation.
+
+// See action.h for an overview of this class and other Action* classes.
+
+// An ActionProcessor keeps a queue of Actions and processes them in order.
+
+namespace chromeos_update_engine {
+
+class AbstractAction;
+class ActionProcessorDelegate;
+
+class ActionProcessor {
+ public:
+  ActionProcessor();
+
+  virtual ~ActionProcessor();
+
+  // Starts processing the first Action in the queue. If there's a delegate,
+  // when all processing is complete, ProcessingDone() will be called on the
+  // delegate.
+  virtual void StartProcessing();
+
+  // Aborts processing. If an Action is running, it will have
+  // TerminateProcessing() called on it. The Action that was running
+  // will be lost and must be re-enqueued if this Processor is to use it.
+  void StopProcessing();
+
+  // Returns true iff an Action is currently processing.
+  bool IsRunning() const { return nullptr != current_action_; }
+
+  // Adds another Action to the end of the queue.
+  virtual void EnqueueAction(AbstractAction* action);
+
+  // Sets/gets the current delegate. Set to null to remove a delegate.
+  ActionProcessorDelegate* delegate() const { return delegate_; }
+  void set_delegate(ActionProcessorDelegate *delegate) {
+    delegate_ = delegate;
+  }
+
+  // Returns a pointer to the current Action that's processing.
+  AbstractAction* current_action() const {
+    return current_action_;
+  }
+
+  // Called by an action to notify processor that it's done. Caller passes self.
+  void ActionComplete(AbstractAction* actionptr, ErrorCode code);
+
+ private:
+  // Actions that have not yet begun processing, in the order in which
+  // they'll be processed.
+  std::deque<AbstractAction*> actions_;
+
+  // A pointer to the currently processing Action, if any.
+  AbstractAction* current_action_;
+
+  // A pointer to the delegate, or null if none.
+  ActionProcessorDelegate *delegate_;
+  DISALLOW_COPY_AND_ASSIGN(ActionProcessor);
+};
+
+// A delegate object can be used to be notified of events that happen
+// in an ActionProcessor. An instance of this class can be passed to an
+// ActionProcessor to register itself.
+class ActionProcessorDelegate {
+ public:
+  virtual ~ActionProcessorDelegate() = default;
+
+  // Called when all processing in an ActionProcessor has completed. A pointer
+  // to the ActionProcessor is passed. |code| is set to the exit code of the
+  // last completed action.
+  virtual void ProcessingDone(const ActionProcessor* processor,
+                              ErrorCode code) {}
+
+  // Called when processing has stopped. Does not mean that all Actions have
+  // completed. If/when all Actions complete, ProcessingDone() will be called.
+  virtual void ProcessingStopped(const ActionProcessor* processor) {}
+
+  // Called whenever an action has finished processing, either successfully
+  // or otherwise.
+  virtual void ActionCompleted(ActionProcessor* processor,
+                               AbstractAction* action,
+                               ErrorCode code) {}
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_ACTION_PROCESSOR_H_
diff --git a/common/action_processor_unittest.cc b/common/action_processor_unittest.cc
new file mode 100644
index 0000000..8285470
--- /dev/null
+++ b/common/action_processor_unittest.cc
@@ -0,0 +1,190 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/action_processor.h"
+
+#include <gtest/gtest.h>
+#include <string>
+#include "update_engine/common/action.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+using chromeos_update_engine::ActionPipe;
+
+class ActionProcessorTestAction;
+
+template<>
+class ActionTraits<ActionProcessorTestAction> {
+ public:
+  typedef string OutputObjectType;
+  typedef string InputObjectType;
+};
+
+// This is a simple Action class for testing.
+class ActionProcessorTestAction : public Action<ActionProcessorTestAction> {
+ public:
+  typedef string InputObjectType;
+  typedef string OutputObjectType;
+  ActionPipe<string>* in_pipe() { return in_pipe_.get(); }
+  ActionPipe<string>* out_pipe() { return out_pipe_.get(); }
+  ActionProcessor* processor() { return processor_; }
+  void PerformAction() {}
+  void CompleteAction() {
+    ASSERT_TRUE(processor());
+    processor()->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  string Type() const { return "ActionProcessorTestAction"; }
+};
+
+class ActionProcessorTest : public ::testing::Test { };
+
+// This test creates two simple Actions and sends a message via an ActionPipe
+// from one to the other.
+TEST(ActionProcessorTest, SimpleTest) {
+  ActionProcessorTestAction action;
+  ActionProcessor action_processor;
+  EXPECT_FALSE(action_processor.IsRunning());
+  action_processor.EnqueueAction(&action);
+  EXPECT_FALSE(action_processor.IsRunning());
+  EXPECT_FALSE(action.IsRunning());
+  action_processor.StartProcessing();
+  EXPECT_TRUE(action_processor.IsRunning());
+  EXPECT_TRUE(action.IsRunning());
+  EXPECT_EQ(action_processor.current_action(), &action);
+  action.CompleteAction();
+  EXPECT_FALSE(action_processor.IsRunning());
+  EXPECT_FALSE(action.IsRunning());
+}
+
+namespace {
+class MyActionProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  explicit MyActionProcessorDelegate(const ActionProcessor* processor)
+      : processor_(processor),
+        processing_done_called_(false),
+        processing_stopped_called_(false),
+        action_completed_called_(false),
+        action_exit_code_(ErrorCode::kError) {}
+
+  virtual void ProcessingDone(const ActionProcessor* processor,
+                              ErrorCode code) {
+    EXPECT_EQ(processor_, processor);
+    EXPECT_FALSE(processing_done_called_);
+    processing_done_called_ = true;
+  }
+  virtual void ProcessingStopped(const ActionProcessor* processor) {
+    EXPECT_EQ(processor_, processor);
+    EXPECT_FALSE(processing_stopped_called_);
+    processing_stopped_called_ = true;
+  }
+  virtual void ActionCompleted(ActionProcessor* processor,
+                               AbstractAction* action,
+                               ErrorCode code) {
+    EXPECT_EQ(processor_, processor);
+    EXPECT_FALSE(action_completed_called_);
+    action_completed_called_ = true;
+    action_exit_code_ = code;
+  }
+
+  const ActionProcessor* processor_;
+  bool processing_done_called_;
+  bool processing_stopped_called_;
+  bool action_completed_called_;
+  ErrorCode action_exit_code_;
+};
+}  // namespace
+
+TEST(ActionProcessorTest, DelegateTest) {
+  ActionProcessorTestAction action;
+  ActionProcessor action_processor;
+  MyActionProcessorDelegate delegate(&action_processor);
+  action_processor.set_delegate(&delegate);
+
+  action_processor.EnqueueAction(&action);
+  action_processor.StartProcessing();
+  action.CompleteAction();
+  action_processor.set_delegate(nullptr);
+  EXPECT_TRUE(delegate.processing_done_called_);
+  EXPECT_TRUE(delegate.action_completed_called_);
+}
+
+TEST(ActionProcessorTest, StopProcessingTest) {
+  ActionProcessorTestAction action;
+  ActionProcessor action_processor;
+  MyActionProcessorDelegate delegate(&action_processor);
+  action_processor.set_delegate(&delegate);
+
+  action_processor.EnqueueAction(&action);
+  action_processor.StartProcessing();
+  action_processor.StopProcessing();
+  action_processor.set_delegate(nullptr);
+  EXPECT_TRUE(delegate.processing_stopped_called_);
+  EXPECT_FALSE(delegate.action_completed_called_);
+  EXPECT_FALSE(action_processor.IsRunning());
+  EXPECT_EQ(nullptr, action_processor.current_action());
+}
+
+TEST(ActionProcessorTest, ChainActionsTest) {
+  ActionProcessorTestAction action1, action2;
+  ActionProcessor action_processor;
+  action_processor.EnqueueAction(&action1);
+  action_processor.EnqueueAction(&action2);
+  action_processor.StartProcessing();
+  EXPECT_EQ(&action1, action_processor.current_action());
+  EXPECT_TRUE(action_processor.IsRunning());
+  action1.CompleteAction();
+  EXPECT_EQ(&action2, action_processor.current_action());
+  EXPECT_TRUE(action_processor.IsRunning());
+  action2.CompleteAction();
+  EXPECT_EQ(nullptr, action_processor.current_action());
+  EXPECT_FALSE(action_processor.IsRunning());
+}
+
+TEST(ActionProcessorTest, DtorTest) {
+  ActionProcessorTestAction action1, action2;
+  {
+    ActionProcessor action_processor;
+    action_processor.EnqueueAction(&action1);
+    action_processor.EnqueueAction(&action2);
+    action_processor.StartProcessing();
+  }
+  EXPECT_EQ(nullptr, action1.processor());
+  EXPECT_FALSE(action1.IsRunning());
+  EXPECT_EQ(nullptr, action2.processor());
+  EXPECT_FALSE(action2.IsRunning());
+}
+
+TEST(ActionProcessorTest, DefaultDelegateTest) {
+  // Just make sure it doesn't crash
+  ActionProcessorTestAction action;
+  ActionProcessor action_processor;
+  ActionProcessorDelegate delegate;
+  action_processor.set_delegate(&delegate);
+
+  action_processor.EnqueueAction(&action);
+  action_processor.StartProcessing();
+  action.CompleteAction();
+
+  action_processor.EnqueueAction(&action);
+  action_processor.StartProcessing();
+  action_processor.StopProcessing();
+
+  action_processor.set_delegate(nullptr);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/action_unittest.cc b/common/action_unittest.cc
new file mode 100644
index 0000000..dcdce17
--- /dev/null
+++ b/common/action_unittest.cc
@@ -0,0 +1,76 @@
+//
+// Copyright (C) 2010 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 "update_engine/common/action.h"
+
+#include <gtest/gtest.h>
+#include <string>
+#include "update_engine/common/action_processor.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+using chromeos_update_engine::ActionPipe;
+
+class ActionTestAction;
+
+template<>
+class ActionTraits<ActionTestAction> {
+ public:
+  typedef string OutputObjectType;
+  typedef string InputObjectType;
+};
+
+// This is a simple Action class for testing.
+class ActionTestAction : public Action<ActionTestAction> {
+ public:
+  typedef string InputObjectType;
+  typedef string OutputObjectType;
+  ActionPipe<string>* in_pipe() { return in_pipe_.get(); }
+  ActionPipe<string>* out_pipe() { return out_pipe_.get(); }
+  ActionProcessor* processor() { return processor_; }
+  void PerformAction() {}
+  void CompleteAction() {
+    ASSERT_TRUE(processor());
+    processor()->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  string Type() const { return "ActionTestAction"; }
+};
+
+class ActionTest : public ::testing::Test { };
+
+// This test creates two simple Actions and sends a message via an ActionPipe
+// from one to the other.
+TEST(ActionTest, SimpleTest) {
+  ActionTestAction action;
+
+  EXPECT_FALSE(action.in_pipe());
+  EXPECT_FALSE(action.out_pipe());
+  EXPECT_FALSE(action.processor());
+  EXPECT_FALSE(action.IsRunning());
+
+  ActionProcessor action_processor;
+  action_processor.EnqueueAction(&action);
+  EXPECT_EQ(&action_processor, action.processor());
+
+  action_processor.StartProcessing();
+  EXPECT_TRUE(action.IsRunning());
+  action.CompleteAction();
+  EXPECT_FALSE(action.IsRunning());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/boot_control.h b/common/boot_control.h
new file mode 100644
index 0000000..1463015
--- /dev/null
+++ b/common/boot_control.h
@@ -0,0 +1,35 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_BOOT_CONTROL_H_
+#define UPDATE_ENGINE_COMMON_BOOT_CONTROL_H_
+
+#include <memory>
+
+#include "update_engine/common/boot_control_interface.h"
+
+namespace chromeos_update_engine {
+namespace boot_control {
+
+// The real BootControlInterface is platform-specific. This factory function
+// creates a new BootControlInterface instance for the current platform. If
+// this fails nullptr is returned.
+std::unique_ptr<BootControlInterface> CreateBootControl();
+
+}  // namespace boot_control
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_BOOT_CONTROL_H_
diff --git a/common/boot_control_chromeos_unittest.cc b/common/boot_control_chromeos_unittest.cc
new file mode 100644
index 0000000..4c218c0
--- /dev/null
+++ b/common/boot_control_chromeos_unittest.cc
@@ -0,0 +1,70 @@
+//
+// Copyright (C) 2015 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 "update_engine/common/boot_control_chromeos.h"
+
+#include <gtest/gtest.h>
+
+namespace chromeos_update_engine {
+
+class BootControlChromeOSTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    // We don't run Init() for bootctl_, we set its internal values instead.
+    bootctl_.num_slots_ = 2;
+    bootctl_.current_slot_ = 0;
+    bootctl_.boot_disk_name_ = "/dev/null";
+  }
+
+  BootControlChromeOS bootctl_;  // BootControlChromeOS under test.
+};
+
+TEST_F(BootControlChromeOSTest, SysfsBlockDeviceTest) {
+  EXPECT_EQ("/sys/block/sda", bootctl_.SysfsBlockDevice("/dev/sda"));
+  EXPECT_EQ("", bootctl_.SysfsBlockDevice("/foo/sda"));
+  EXPECT_EQ("", bootctl_.SysfsBlockDevice("/dev/foo/bar"));
+  EXPECT_EQ("", bootctl_.SysfsBlockDevice("/"));
+  EXPECT_EQ("", bootctl_.SysfsBlockDevice("./"));
+  EXPECT_EQ("", bootctl_.SysfsBlockDevice(""));
+}
+
+TEST_F(BootControlChromeOSTest, GetPartitionNumberTest) {
+  // The partition name should not be case-sensitive.
+  EXPECT_EQ(2, bootctl_.GetPartitionNumber("kernel", 0));
+  EXPECT_EQ(2, bootctl_.GetPartitionNumber("boot", 0));
+  EXPECT_EQ(2, bootctl_.GetPartitionNumber("KERNEL", 0));
+  EXPECT_EQ(2, bootctl_.GetPartitionNumber("BOOT", 0));
+
+  EXPECT_EQ(3, bootctl_.GetPartitionNumber("ROOT", 0));
+  EXPECT_EQ(3, bootctl_.GetPartitionNumber("system", 0));
+
+  EXPECT_EQ(3, bootctl_.GetPartitionNumber("ROOT", 0));
+  EXPECT_EQ(3, bootctl_.GetPartitionNumber("system", 0));
+
+  // Slot B.
+  EXPECT_EQ(4, bootctl_.GetPartitionNumber("KERNEL", 1));
+  EXPECT_EQ(5, bootctl_.GetPartitionNumber("ROOT", 1));
+
+  // Slot C doesn't exists.
+  EXPECT_EQ(-1, bootctl_.GetPartitionNumber("KERNEL", 2));
+  EXPECT_EQ(-1, bootctl_.GetPartitionNumber("ROOT", 2));
+
+  // Non A/B partitions are ignored.
+  EXPECT_EQ(-1, bootctl_.GetPartitionNumber("OEM", 0));
+  EXPECT_EQ(-1, bootctl_.GetPartitionNumber("A little panda", 0));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/boot_control_interface.h b/common/boot_control_interface.h
new file mode 100644
index 0000000..659b388
--- /dev/null
+++ b/common/boot_control_interface.h
@@ -0,0 +1,98 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_BOOT_CONTROL_INTERFACE_H_
+#define UPDATE_ENGINE_COMMON_BOOT_CONTROL_INTERFACE_H_
+
+#include <climits>
+#include <string>
+
+#include <base/callback.h>
+#include <base/macros.h>
+
+namespace chromeos_update_engine {
+
+// The abstract boot control interface defines the interaction with the
+// platform's bootloader hiding vendor-specific details from the rest of
+// update_engine. This interface is used for controlling where the device should
+// boot from.
+class BootControlInterface {
+ public:
+  using Slot = unsigned int;
+
+  static const Slot kInvalidSlot = UINT_MAX;
+
+  virtual ~BootControlInterface() = default;
+
+  // Return the number of update slots in the system. A system will normally
+  // have two slots, named "A" and "B" in the documentation, but sometimes
+  // images running from other media can have only one slot, like some USB
+  // image. Systems with only one slot won't be able to update.
+  virtual unsigned int GetNumSlots() const = 0;
+
+  // Return the slot where we are running the system from. On success, the
+  // result is a number between 0 and GetNumSlots() - 1. Otherwise, log an error
+  // and return kInvalidSlot.
+  virtual Slot GetCurrentSlot() const = 0;
+
+  // Determines the block device for the given partition name and slot number.
+  // The |slot| number must be between 0 and GetNumSlots() - 1 and the
+  // |partition_name| is a platform-specific name that identifies a partition on
+  // every slot. On success, returns true and stores the block device in
+  // |device|.
+  virtual bool GetPartitionDevice(const std::string& partition_name,
+                                  Slot slot,
+                                  std::string* device) const = 0;
+
+  // Returns whether the passed |slot| is marked as bootable. Returns false if
+  // the slot is invalid.
+  virtual bool IsSlotBootable(Slot slot) const = 0;
+
+  // Mark the specified slot unbootable. No other slot flags are modified.
+  // Returns true on success.
+  virtual bool MarkSlotUnbootable(Slot slot) = 0;
+
+  // Set the passed |slot| as the preferred boot slot. Returns whether it
+  // succeeded setting the active slot. If succeeded, on next boot the
+  // bootloader will attempt to load the |slot| marked as active. Note that this
+  // method doesn't change the value of GetCurrentSlot() on the current boot.
+  virtual bool SetActiveBootSlot(Slot slot) = 0;
+
+  // Mark the current slot as successfully booted asynchronously. No other slot
+  // flags are modified. Returns false if it was not able to schedule the
+  // operation, otherwise, returns true and calls the |callback| with the result
+  // of the operation.
+  virtual bool MarkBootSuccessfulAsync(base::Callback<void(bool)> callback) = 0;
+
+  // Return a human-readable slot name used for logging.
+  static std::string SlotName(Slot slot) {
+    if (slot == kInvalidSlot)
+      return "INVALID";
+    if (slot < 26)
+      return std::string(1, 'A' + slot);
+    return "TOO_BIG";
+  }
+
+ protected:
+  BootControlInterface() = default;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(BootControlInterface);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_BOOT_CONTROL_INTERFACE_H_
diff --git a/common/boot_control_stub.cc b/common/boot_control_stub.cc
new file mode 100644
index 0000000..2de0c82
--- /dev/null
+++ b/common/boot_control_stub.cc
@@ -0,0 +1,62 @@
+//
+// Copyright (C) 2015 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 "update_engine/common/boot_control_stub.h"
+
+#include <base/logging.h>
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+unsigned int BootControlStub::GetNumSlots() const {
+  return 0;
+}
+
+BootControlInterface::Slot BootControlStub::GetCurrentSlot() const {
+  LOG(ERROR) << __FUNCTION__ << " should never be called.";
+  return 0;
+}
+
+bool BootControlStub::GetPartitionDevice(const string& partition_name,
+                                         Slot slot,
+                                         string* device) const {
+  LOG(ERROR) << __FUNCTION__ << " should never be called.";
+  return false;
+}
+
+bool BootControlStub::IsSlotBootable(Slot slot) const {
+  LOG(ERROR) << __FUNCTION__ << " should never be called.";
+  return false;
+}
+
+bool BootControlStub::MarkSlotUnbootable(Slot slot) {
+  LOG(ERROR) << __FUNCTION__ << " should never be called.";
+  return false;
+}
+
+bool BootControlStub::SetActiveBootSlot(Slot slot) {
+  LOG(ERROR) << __FUNCTION__ << " should never be called.";
+  return false;
+}
+
+bool BootControlStub::MarkBootSuccessfulAsync(
+    base::Callback<void(bool)> callback) {
+  // This is expected to be called on update_engine startup.
+  return false;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/boot_control_stub.h b/common/boot_control_stub.h
new file mode 100644
index 0000000..7832adc
--- /dev/null
+++ b/common/boot_control_stub.h
@@ -0,0 +1,55 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_BOOT_CONTROL_STUB_H_
+#define UPDATE_ENGINE_COMMON_BOOT_CONTROL_STUB_H_
+
+#include <string>
+
+#include "update_engine/common/boot_control_interface.h"
+
+namespace chromeos_update_engine {
+
+// An implementation of the BootControlInterface that does nothing,
+// typically used when e.g. an underlying HAL implementation cannot be
+// loaded or doesn't exist.
+//
+// You are gauranteed that the implementation of GetNumSlots() method
+// always returns 0. This can be used to identify that this
+// implementation is in use.
+class BootControlStub : public BootControlInterface {
+ public:
+  BootControlStub() = default;
+  ~BootControlStub() = default;
+
+  // BootControlInterface overrides.
+  unsigned int GetNumSlots() const override;
+  BootControlInterface::Slot GetCurrentSlot() const override;
+  bool GetPartitionDevice(const std::string& partition_name,
+                          BootControlInterface::Slot slot,
+                          std::string* device) const override;
+  bool IsSlotBootable(BootControlInterface::Slot slot) const override;
+  bool MarkSlotUnbootable(BootControlInterface::Slot slot) override;
+  bool SetActiveBootSlot(BootControlInterface::Slot slot) override;
+  bool MarkBootSuccessfulAsync(base::Callback<void(bool)> callback) override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(BootControlStub);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_BOOT_CONTROL_STUB_H_
diff --git a/common/certificate_checker.cc b/common/certificate_checker.cc
new file mode 100644
index 0000000..86df950
--- /dev/null
+++ b/common/certificate_checker.cc
@@ -0,0 +1,204 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/certificate_checker.h"
+
+#include <string>
+
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <curl/curl.h>
+#include <openssl/evp.h>
+#include <openssl/ssl.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+bool OpenSSLWrapper::GetCertificateDigest(X509_STORE_CTX* x509_ctx,
+                                          int* out_depth,
+                                          unsigned int* out_digest_length,
+                                          uint8_t* out_digest) const {
+  TEST_AND_RETURN_FALSE(out_digest);
+  X509* certificate = X509_STORE_CTX_get_current_cert(x509_ctx);
+  TEST_AND_RETURN_FALSE(certificate);
+  int depth = X509_STORE_CTX_get_error_depth(x509_ctx);
+  if (out_depth)
+    *out_depth = depth;
+
+  unsigned int len;
+  const EVP_MD* digest_function = EVP_sha256();
+  bool success = X509_digest(certificate, digest_function, out_digest, &len);
+
+  if (success && out_digest_length)
+    *out_digest_length = len;
+  return success;
+}
+
+// static
+CertificateChecker* CertificateChecker::cert_checker_singleton_ = nullptr;
+
+CertificateChecker::CertificateChecker(PrefsInterface* prefs,
+                                       OpenSSLWrapper* openssl_wrapper)
+    : prefs_(prefs), openssl_wrapper_(openssl_wrapper) {
+}
+
+CertificateChecker::~CertificateChecker() {
+  if (cert_checker_singleton_ == this)
+    cert_checker_singleton_ = nullptr;
+}
+
+void CertificateChecker::Init() {
+  CHECK(cert_checker_singleton_ == nullptr);
+  cert_checker_singleton_ = this;
+}
+
+// static
+CURLcode CertificateChecker::ProcessSSLContext(CURL* curl_handle,
+                                               SSL_CTX* ssl_ctx,
+                                               void* ptr) {
+  ServerToCheck* server_to_check = reinterpret_cast<ServerToCheck*>(ptr);
+
+  if (!cert_checker_singleton_) {
+    DLOG(WARNING) << "No CertificateChecker singleton initialized.";
+    return CURLE_FAILED_INIT;
+  }
+
+  // From here we set the SSL_CTX to another callback, from the openssl library,
+  // which will be called after each server certificate is validated. However,
+  // since openssl does not allow us to pass our own data pointer to the
+  // callback, the certificate check will have to be done statically. Since we
+  // need to know which update server we are using in order to check the
+  // certificate, we hardcode Chrome OS's two known update servers here, and
+  // define a different static callback for each. Since this code should only
+  // run in official builds, this should not be a problem. However, if an update
+  // server different from the ones listed here is used, the check will not
+  // take place.
+  int (*verify_callback)(int, X509_STORE_CTX*);
+  switch (*server_to_check) {
+    case ServerToCheck::kDownload:
+      verify_callback = &CertificateChecker::VerifySSLCallbackDownload;
+      break;
+    case ServerToCheck::kUpdate:
+      verify_callback = &CertificateChecker::VerifySSLCallbackUpdate;
+      break;
+    case ServerToCheck::kNone:
+      verify_callback = nullptr;
+      break;
+  }
+
+  SSL_CTX_set_verify(ssl_ctx, SSL_VERIFY_PEER, verify_callback);
+  return CURLE_OK;
+}
+
+// static
+int CertificateChecker::VerifySSLCallbackDownload(int preverify_ok,
+                                                  X509_STORE_CTX* x509_ctx) {
+  return VerifySSLCallback(preverify_ok, x509_ctx, ServerToCheck::kDownload);
+}
+
+// static
+int CertificateChecker::VerifySSLCallbackUpdate(int preverify_ok,
+                                                X509_STORE_CTX* x509_ctx) {
+  return VerifySSLCallback(preverify_ok, x509_ctx, ServerToCheck::kUpdate);
+}
+
+// static
+int CertificateChecker::VerifySSLCallback(int preverify_ok,
+                                          X509_STORE_CTX* x509_ctx,
+                                          ServerToCheck server_to_check) {
+  CHECK(cert_checker_singleton_ != nullptr);
+  return cert_checker_singleton_->CheckCertificateChange(
+      preverify_ok, x509_ctx, server_to_check) ? 1 : 0;
+}
+
+bool CertificateChecker::CheckCertificateChange(int preverify_ok,
+                                                X509_STORE_CTX* x509_ctx,
+                                                ServerToCheck server_to_check) {
+  TEST_AND_RETURN_FALSE(prefs_ != nullptr);
+
+  // If pre-verification failed, we are not interested in the current
+  // certificate. We store a report to UMA and just propagate the fail result.
+  if (!preverify_ok) {
+    NotifyCertificateChecked(server_to_check, CertificateCheckResult::kFailed);
+    return false;
+  }
+
+  int depth;
+  unsigned int digest_length;
+  uint8_t digest[EVP_MAX_MD_SIZE];
+
+  if (!openssl_wrapper_->GetCertificateDigest(x509_ctx,
+                                              &depth,
+                                              &digest_length,
+                                              digest)) {
+    LOG(WARNING) << "Failed to generate digest of X509 certificate "
+                 << "from update server.";
+    NotifyCertificateChecked(server_to_check, CertificateCheckResult::kValid);
+    return true;
+  }
+
+  // We convert the raw bytes of the digest to an hex string, for storage in
+  // prefs.
+  string digest_string = base::HexEncode(digest, digest_length);
+
+  string storage_key =
+      base::StringPrintf("%s-%d-%d", kPrefsUpdateServerCertificate,
+                         static_cast<int>(server_to_check), depth);
+  string stored_digest;
+  // If there's no stored certificate, we just store the current one and return.
+  if (!prefs_->GetString(storage_key, &stored_digest)) {
+    if (!prefs_->SetString(storage_key, digest_string)) {
+      LOG(WARNING) << "Failed to store server certificate on storage key "
+                   << storage_key;
+    }
+    NotifyCertificateChecked(server_to_check, CertificateCheckResult::kValid);
+    return true;
+  }
+
+  // Certificate changed, we store a report to UMA and store the most recent
+  // certificate.
+  if (stored_digest != digest_string) {
+    if (!prefs_->SetString(storage_key, digest_string)) {
+      LOG(WARNING) << "Failed to store server certificate on storage key "
+                   << storage_key;
+    }
+    LOG(INFO) << "Certificate changed from " << stored_digest << " to "
+              << digest_string << ".";
+    NotifyCertificateChecked(server_to_check,
+                             CertificateCheckResult::kValidChanged);
+    return true;
+  }
+
+  NotifyCertificateChecked(server_to_check, CertificateCheckResult::kValid);
+  // Since we don't perform actual SSL verification, we return success.
+  return true;
+}
+
+void CertificateChecker::NotifyCertificateChecked(
+    ServerToCheck server_to_check,
+    CertificateCheckResult result) {
+  if (observer_)
+    observer_->CertificateChecked(server_to_check, result);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/certificate_checker.h b/common/certificate_checker.h
new file mode 100644
index 0000000..c785192
--- /dev/null
+++ b/common/certificate_checker.h
@@ -0,0 +1,175 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_CERTIFICATE_CHECKER_H_
+#define UPDATE_ENGINE_COMMON_CERTIFICATE_CHECKER_H_
+
+#include <curl/curl.h>
+#include <openssl/ssl.h>
+
+#include <string>
+
+#include <base/macros.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+namespace chromeos_update_engine {
+
+class PrefsInterface;
+
+// Wrapper for openssl operations with the certificates.
+class OpenSSLWrapper {
+ public:
+  OpenSSLWrapper() = default;
+  virtual ~OpenSSLWrapper() = default;
+
+  // Takes an openssl X509_STORE_CTX, extracts the corresponding certificate
+  // from it and calculates its fingerprint (SHA256 digest). Returns true on
+  // success and false otherwise.
+  //
+  // |x509_ctx| is the pointer to the openssl object that holds the certificate.
+  // |out_depth| is the depth of the current certificate, in the certificate
+  // chain.
+  // |out_digest_length| is the length of the generated digest.
+  // |out_digest| is the byte array where the digest itself will be written.
+  // It should be big enough to hold a SHA1 digest (e.g. EVP_MAX_MD_SIZE).
+  virtual bool GetCertificateDigest(X509_STORE_CTX* x509_ctx,
+                                    int* out_depth,
+                                    unsigned int* out_digest_length,
+                                    uint8_t* out_digest) const;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(OpenSSLWrapper);
+};
+
+// The values in this enum are replicated in the metrics server. See metrics.h
+// for instructions on how to update these values in the server side.
+enum class CertificateCheckResult {
+  // The certificate is valid and the same as seen before or the first time we
+  // see a certificate.
+  kValid,
+  // The certificate is valid, but is different than a previously seen
+  // certificate for the selected server.
+  kValidChanged,
+  // The certificate validation failed.
+  kFailed,
+
+  // This value must be the last entry.
+  kNumConstants
+};
+
+// These values are used to generate the keys of files persisted via prefs.
+// This means that changing these will cause loss of information on metrics
+// reporting, during the transition. These values are also mapped to a metric
+// name in metrics.cc, so adding values here requires to assign a new metric
+// name in that file.
+enum class ServerToCheck {
+  kUpdate = 0,
+  kDownload,
+
+  // Ignore this server.
+  kNone,
+};
+
+// Responsible for checking whether update server certificates change, and
+// reporting to UMA when this happens. Since all state information is persisted,
+// and openssl forces us to use a static callback with no data pointer, this
+// class is entirely static.
+class CertificateChecker {
+ public:
+  class Observer {
+   public:
+    virtual ~Observer() = default;
+
+    // Called whenever a certificate is checked for the server |server_to_check|
+    // passing the result of said certificate check.
+    virtual void CertificateChecked(ServerToCheck server_to_check,
+                                    CertificateCheckResult result) = 0;
+  };
+
+  CertificateChecker(PrefsInterface* prefs, OpenSSLWrapper* openssl_wrapper);
+  ~CertificateChecker();
+
+  // This callback is called by libcurl just before the initialization of an
+  // SSL connection after having processed all other SSL related options. Used
+  // to check if server certificates change. |cert_checker| is expected to be a
+  // pointer to the CertificateChecker instance.
+  static CURLcode ProcessSSLContext(CURL* curl_handle,
+                                    SSL_CTX* ssl_ctx,
+                                    void* cert_checker);
+
+  // Initialize this class as the singleton instance. Only one instance can be
+  // initialized at a time and it should be initialized before other methods
+  // can be used.
+  void Init();
+
+  // Set the certificate observer to the passed instance. To remove the
+  // observer, pass a nullptr. The |observer| instance must be valid while this
+  // CertificateChecker verifies certificates.
+  void SetObserver(Observer* observer) { observer_ = observer; }
+
+ private:
+  FRIEND_TEST(CertificateCheckerTest, NewCertificate);
+  FRIEND_TEST(CertificateCheckerTest, SameCertificate);
+  FRIEND_TEST(CertificateCheckerTest, ChangedCertificate);
+  FRIEND_TEST(CertificateCheckerTest, FailedCertificate);
+
+  // These callbacks are asynchronously called by openssl after initial SSL
+  // verification. They are used to perform any additional security verification
+  // on the connection, but we use them here to get hold of the server
+  // certificate, in order to determine if it has changed since the last
+  // connection. Since openssl forces us to do this statically, we define two
+  // different callbacks for the two different official update servers, and only
+  // assign the correspondent one. The assigned callback is then called once per
+  // each certificate on the server and returns 1 for success and 0 for failure.
+  static int VerifySSLCallbackDownload(int preverify_ok,
+                                       X509_STORE_CTX* x509_ctx);
+  static int VerifySSLCallbackUpdate(int preverify_ok,
+                                     X509_STORE_CTX* x509_ctx);
+  static int VerifySSLCallback(int preverify_ok,
+                               X509_STORE_CTX* x509_ctx,
+                               ServerToCheck server_to_check);
+
+  // Checks if server certificate stored in |x509_ctx| has changed since last
+  // connection to that same server, specified by |server_to_check|.
+  // This is called by the callbacks defined above. The result of the
+  // certificate check is passed to the observer, if any. Returns true on
+  // success and false otherwise.
+  bool CheckCertificateChange(int preverify_ok,
+                              X509_STORE_CTX* x509_ctx,
+                              ServerToCheck server_to_check);
+
+  // Notifies the observer, if any, of a certificate checking.
+  void NotifyCertificateChecked(ServerToCheck server_to_check,
+                                CertificateCheckResult result);
+
+  // The CertificateChecker singleton instance.
+  static CertificateChecker* cert_checker_singleton_;
+
+  // Prefs instance used to store the certificates seen in the past.
+  PrefsInterface* prefs_;
+
+  // The wrapper for openssl operations.
+  OpenSSLWrapper* openssl_wrapper_;
+
+  // The observer called whenever a certificate is checked, if not null.
+  Observer* observer_{nullptr};
+
+  DISALLOW_COPY_AND_ASSIGN(CertificateChecker);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_CERTIFICATE_CHECKER_H_
diff --git a/common/certificate_checker_unittest.cc b/common/certificate_checker_unittest.cc
new file mode 100644
index 0000000..c30acc5
--- /dev/null
+++ b/common/certificate_checker_unittest.cc
@@ -0,0 +1,140 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/certificate_checker.h"
+
+#include <string>
+
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/mock_certificate_checker.h"
+#include "update_engine/common/mock_prefs.h"
+
+using ::testing::DoAll;
+using ::testing::Return;
+using ::testing::SetArgumentPointee;
+using ::testing::SetArrayArgument;
+using ::testing::_;
+using std::string;
+
+namespace chromeos_update_engine {
+
+class MockCertificateCheckObserver : public CertificateChecker::Observer {
+ public:
+  MOCK_METHOD2(CertificateChecked,
+               void(ServerToCheck server_to_check,
+                    CertificateCheckResult result));
+};
+
+class CertificateCheckerTest : public testing::Test {
+ protected:
+  void SetUp() override {
+    cert_key_ = base::StringPrintf("%s-%d-%d",
+                                   cert_key_prefix_.c_str(),
+                                   static_cast<int>(server_to_check_),
+                                   depth_);
+    cert_checker.Init();
+    cert_checker.SetObserver(&observer_);
+  }
+
+  void TearDown() override {
+    cert_checker.SetObserver(nullptr);
+  }
+
+  MockPrefs prefs_;
+  MockOpenSSLWrapper openssl_wrapper_;
+  // Parameters of our mock certificate digest.
+  int depth_{0};
+  unsigned int length_{4};
+  uint8_t digest_[4]{0x17, 0x7D, 0x07, 0x5F};
+  string digest_hex_{"177D075F"};
+  string diff_digest_hex_{"1234ABCD"};
+  string cert_key_prefix_{kPrefsUpdateServerCertificate};
+  ServerToCheck server_to_check_{ServerToCheck::kUpdate};
+  string cert_key_;
+
+  testing::StrictMock<MockCertificateCheckObserver> observer_;
+  CertificateChecker cert_checker{&prefs_, &openssl_wrapper_};
+};
+
+// check certificate change, new
+TEST_F(CertificateCheckerTest, NewCertificate) {
+  EXPECT_CALL(openssl_wrapper_, GetCertificateDigest(nullptr, _, _, _))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(depth_),
+          SetArgumentPointee<2>(length_),
+          SetArrayArgument<3>(digest_, digest_ + 4),
+          Return(true)));
+  EXPECT_CALL(prefs_, GetString(cert_key_, _)).WillOnce(Return(false));
+  EXPECT_CALL(prefs_, SetString(cert_key_, digest_hex_)).WillOnce(Return(true));
+  EXPECT_CALL(observer_,
+              CertificateChecked(server_to_check_,
+                                 CertificateCheckResult::kValid));
+  ASSERT_TRUE(
+      cert_checker.CheckCertificateChange(1, nullptr, server_to_check_));
+}
+
+// check certificate change, unchanged
+TEST_F(CertificateCheckerTest, SameCertificate) {
+  EXPECT_CALL(openssl_wrapper_, GetCertificateDigest(nullptr, _, _, _))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(depth_),
+          SetArgumentPointee<2>(length_),
+          SetArrayArgument<3>(digest_, digest_ + 4),
+          Return(true)));
+  EXPECT_CALL(prefs_, GetString(cert_key_, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(digest_hex_), Return(true)));
+  EXPECT_CALL(prefs_, SetString(_, _)).Times(0);
+  EXPECT_CALL(observer_,
+              CertificateChecked(server_to_check_,
+                                 CertificateCheckResult::kValid));
+  ASSERT_TRUE(
+      cert_checker.CheckCertificateChange(1, nullptr, server_to_check_));
+}
+
+// check certificate change, changed
+TEST_F(CertificateCheckerTest, ChangedCertificate) {
+  EXPECT_CALL(openssl_wrapper_, GetCertificateDigest(nullptr, _, _, _))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(depth_),
+          SetArgumentPointee<2>(length_),
+          SetArrayArgument<3>(digest_, digest_ + 4),
+          Return(true)));
+  EXPECT_CALL(prefs_, GetString(cert_key_, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(diff_digest_hex_), Return(true)));
+  EXPECT_CALL(observer_,
+              CertificateChecked(server_to_check_,
+                                 CertificateCheckResult::kValidChanged));
+  EXPECT_CALL(prefs_, SetString(cert_key_, digest_hex_)).WillOnce(Return(true));
+  ASSERT_TRUE(
+      cert_checker.CheckCertificateChange(1, nullptr, server_to_check_));
+}
+
+// check certificate change, failed
+TEST_F(CertificateCheckerTest, FailedCertificate) {
+  EXPECT_CALL(observer_, CertificateChecked(server_to_check_,
+                                            CertificateCheckResult::kFailed));
+  EXPECT_CALL(prefs_, GetString(_, _)).Times(0);
+  EXPECT_CALL(openssl_wrapper_, GetCertificateDigest(_, _, _, _)).Times(0);
+  ASSERT_FALSE(
+      cert_checker.CheckCertificateChange(0, nullptr, server_to_check_));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/clock.cc b/common/clock.cc
new file mode 100644
index 0000000..f0eff44
--- /dev/null
+++ b/common/clock.cc
@@ -0,0 +1,58 @@
+//
+// Copyright (C) 2013 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 "update_engine/common/clock.h"
+
+#include <time.h>
+
+namespace chromeos_update_engine {
+
+base::Time Clock::GetWallclockTime() {
+  return base::Time::Now();
+}
+
+base::Time Clock::GetMonotonicTime() {
+  struct timespec now_ts;
+  if (clock_gettime(CLOCK_MONOTONIC_RAW, &now_ts) != 0) {
+    // Avoid logging this as an error as call-sites may call this very
+    // often and we don't want to fill up the disk. Note that this
+    // only fails if running on ancient kernels (CLOCK_MONOTONIC_RAW
+    // was added in Linux 2.6.28) so it never fails on a ChromeOS
+    // device.
+    return base::Time();
+  }
+  struct timeval now_tv;
+  now_tv.tv_sec = now_ts.tv_sec;
+  now_tv.tv_usec = now_ts.tv_nsec/base::Time::kNanosecondsPerMicrosecond;
+  return base::Time::FromTimeVal(now_tv);
+}
+
+base::Time Clock::GetBootTime() {
+  struct timespec now_ts;
+  if (clock_gettime(CLOCK_BOOTTIME, &now_ts) != 0) {
+    // Avoid logging this as an error as call-sites may call this very
+    // often and we don't want to fill up the disk. Note that this
+    // only fails if running on ancient kernels (CLOCK_BOOTTIME was
+    // added in Linux 2.6.39) so it never fails on a ChromeOS device.
+    return base::Time();
+  }
+  struct timeval now_tv;
+  now_tv.tv_sec = now_ts.tv_sec;
+  now_tv.tv_usec = now_ts.tv_nsec/base::Time::kNanosecondsPerMicrosecond;
+  return base::Time::FromTimeVal(now_tv);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/clock.h b/common/clock.h
new file mode 100644
index 0000000..2f373a7
--- /dev/null
+++ b/common/clock.h
@@ -0,0 +1,41 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_CLOCK_H_
+#define UPDATE_ENGINE_COMMON_CLOCK_H_
+
+#include "update_engine/common/clock_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a clock.
+class Clock : public ClockInterface {
+ public:
+  Clock() {}
+
+  base::Time GetWallclockTime() override;
+
+  base::Time GetMonotonicTime() override;
+
+  base::Time GetBootTime() override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(Clock);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_CLOCK_H_
diff --git a/common/clock_interface.h b/common/clock_interface.h
new file mode 100644
index 0000000..2228983
--- /dev/null
+++ b/common/clock_interface.h
@@ -0,0 +1,54 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_CLOCK_INTERFACE_H_
+#define UPDATE_ENGINE_COMMON_CLOCK_INTERFACE_H_
+
+#include <string>
+
+#include <base/time/time.h>
+
+namespace chromeos_update_engine {
+
+// The clock interface allows access to various system clocks. The
+// sole reason for providing this as an interface is unit testing.
+// Additionally, the sole reason for the methods not being static
+// is also unit testing.
+class ClockInterface {
+ public:
+  virtual ~ClockInterface() = default;
+
+  // Gets the current time e.g. similar to base::Time::Now().
+  virtual base::Time GetWallclockTime() = 0;
+
+  // Returns monotonic time since some unspecified starting point. It
+  // is not increased when the system is sleeping nor is it affected
+  // by NTP or the user changing the time.
+  //
+  // (This is a simple wrapper around clock_gettime(2) / CLOCK_MONOTONIC_RAW.)
+  virtual base::Time GetMonotonicTime() = 0;
+
+  // Returns monotonic time since some unspecified starting point. It
+  // is increased when the system is sleeping but it's not affected
+  // by NTP or the user changing the time.
+  //
+  // (This is a simple wrapper around clock_gettime(2) / CLOCK_BOOTTIME.)
+  virtual base::Time GetBootTime() = 0;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_CLOCK_INTERFACE_H_
diff --git a/common/constants.cc b/common/constants.cc
new file mode 100644
index 0000000..fe4e643
--- /dev/null
+++ b/common/constants.cc
@@ -0,0 +1,90 @@
+//
+// Copyright (C) 2013 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 "update_engine/common/constants.h"
+
+namespace chromeos_update_engine {
+
+const char kPowerwashMarkerFile[] =
+    "/mnt/stateful_partition/factory_install_reset";
+
+const char kPowerwashCommand[] = "safe fast keepimg reason=update_engine\n";
+
+const char kPowerwashSafePrefsSubDirectory[] = "update_engine/prefs";
+
+const char kPrefsSubDirectory[] = "prefs";
+
+const char kStatefulPartition[] = "/mnt/stateful_partition";
+
+// Constants defining keys for the persisted state of update engine.
+const char kPrefsAttemptInProgress[] = "attempt-in-progress";
+const char kPrefsBackoffExpiryTime[] = "backoff-expiry-time";
+const char kPrefsBootId[] = "boot-id";
+const char kPrefsCurrentBytesDownloaded[] = "current-bytes-downloaded";
+const char kPrefsCurrentResponseSignature[] = "current-response-signature";
+const char kPrefsCurrentUrlFailureCount[] = "current-url-failure-count";
+const char kPrefsCurrentUrlIndex[] = "current-url-index";
+const char kPrefsDailyMetricsLastReportedAt[] =
+    "daily-metrics-last-reported-at";
+const char kPrefsDeltaUpdateFailures[] = "delta-update-failures";
+const char kPrefsFullPayloadAttemptNumber[] = "full-payload-attempt-number";
+const char kPrefsInstallDateDays[] = "install-date-days";
+const char kPrefsLastActivePingDay[] = "last-active-ping-day";
+const char kPrefsLastRollCallPingDay[] = "last-roll-call-ping-day";
+const char kPrefsManifestMetadataSize[] = "manifest-metadata-size";
+const char kPrefsMetricsAttemptLastReportingTime[] =
+    "metrics-attempt-last-reporting-time";
+const char kPrefsMetricsCheckLastReportingTime[] =
+    "metrics-check-last-reporting-time";
+const char kPrefsNumReboots[] = "num-reboots";
+const char kPrefsNumResponsesSeen[] = "num-responses-seen";
+const char kPrefsOmahaCohort[] = "omaha-cohort";
+const char kPrefsOmahaCohortHint[] = "omaha-cohort-hint";
+const char kPrefsOmahaCohortName[] = "omaha-cohort-name";
+const char kPrefsP2PEnabled[] = "p2p-enabled";
+const char kPrefsP2PFirstAttemptTimestamp[] = "p2p-first-attempt-timestamp";
+const char kPrefsP2PNumAttempts[] = "p2p-num-attempts";
+const char kPrefsPayloadAttemptNumber[] = "payload-attempt-number";
+const char kPrefsPreviousVersion[] = "previous-version";
+const char kPrefsResumedUpdateFailures[] = "resumed-update-failures";
+const char kPrefsRollbackVersion[] = "rollback-version";
+const char kPrefsChannelOnSlotPrefix[] = "channel-on-slot-";
+const char kPrefsSystemUpdatedMarker[] = "system-updated-marker";
+const char kPrefsTargetVersionAttempt[] = "target-version-attempt";
+const char kPrefsTargetVersionInstalledFrom[] = "target-version-installed-from";
+const char kPrefsTargetVersionUniqueId[] = "target-version-unique-id";
+const char kPrefsTotalBytesDownloaded[] = "total-bytes-downloaded";
+const char kPrefsUpdateCheckCount[] = "update-check-count";
+const char kPrefsUpdateCheckResponseHash[] = "update-check-response-hash";
+const char kPrefsUpdateCompletedBootTime[] = "update-completed-boot-time";
+const char kPrefsUpdateCompletedOnBootId[] = "update-completed-on-boot-id";
+const char kPrefsUpdateDurationUptime[] = "update-duration-uptime";
+const char kPrefsUpdateFirstSeenAt[] = "update-first-seen-at";
+const char kPrefsUpdateOverCellularPermission[] =
+    "update-over-cellular-permission";
+const char kPrefsUpdateServerCertificate[] = "update-server-cert";
+const char kPrefsUpdateStateNextDataLength[] = "update-state-next-data-length";
+const char kPrefsUpdateStateNextDataOffset[] = "update-state-next-data-offset";
+const char kPrefsUpdateStateNextOperation[] = "update-state-next-operation";
+const char kPrefsUpdateStateSHA256Context[] = "update-state-sha-256-context";
+const char kPrefsUpdateStateSignatureBlob[] = "update-state-signature-blob";
+const char kPrefsUpdateStateSignedSHA256Context[] =
+    "update-state-signed-sha-256-context";
+const char kPrefsUpdateTimestampStart[] = "update-timestamp-start";
+const char kPrefsUrlSwitchCount[] = "url-switch-count";
+const char kPrefsWallClockWaitPeriod[] = "wall-clock-wait-period";
+
+}  // namespace chromeos_update_engine
diff --git a/common/constants.h b/common/constants.h
new file mode 100644
index 0000000..f20de8e
--- /dev/null
+++ b/common/constants.h
@@ -0,0 +1,180 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_CONSTANTS_H_
+#define UPDATE_ENGINE_COMMON_CONSTANTS_H_
+
+namespace chromeos_update_engine {
+
+// The name of the marker file used to trigger powerwash when post-install
+// completes successfully so that the device is powerwashed on next reboot.
+extern const char kPowerwashMarkerFile[];
+
+// The contents of the powerwash marker file.
+extern const char kPowerwashCommand[];
+
+// Directory for AU prefs that are preserved across powerwash.
+extern const char kPowerwashSafePrefsSubDirectory[];
+
+// The location where we store the AU preferences (state etc).
+extern const char kPrefsSubDirectory[];
+
+// Path to the stateful partition on the root filesystem.
+extern const char kStatefulPartition[];
+
+// Constants related to preferences.
+extern const char kPrefsAttemptInProgress[];
+extern const char kPrefsBackoffExpiryTime[];
+extern const char kPrefsBootId[];
+extern const char kPrefsCurrentBytesDownloaded[];
+extern const char kPrefsCurrentResponseSignature[];
+extern const char kPrefsCurrentUrlFailureCount[];
+extern const char kPrefsCurrentUrlIndex[];
+extern const char kPrefsDailyMetricsLastReportedAt[];
+extern const char kPrefsDeltaUpdateFailures[];
+extern const char kPrefsFullPayloadAttemptNumber[];
+extern const char kPrefsInstallDateDays[];
+extern const char kPrefsLastActivePingDay[];
+extern const char kPrefsLastRollCallPingDay[];
+extern const char kPrefsManifestMetadataSize[];
+extern const char kPrefsMetricsAttemptLastReportingTime[];
+extern const char kPrefsMetricsCheckLastReportingTime[];
+extern const char kPrefsNumReboots[];
+extern const char kPrefsNumResponsesSeen[];
+extern const char kPrefsOmahaCohort[];
+extern const char kPrefsOmahaCohortHint[];
+extern const char kPrefsOmahaCohortName[];
+extern const char kPrefsP2PEnabled[];
+extern const char kPrefsP2PFirstAttemptTimestamp[];
+extern const char kPrefsP2PNumAttempts[];
+extern const char kPrefsPayloadAttemptNumber[];
+extern const char kPrefsPreviousVersion[];
+extern const char kPrefsResumedUpdateFailures[];
+extern const char kPrefsRollbackVersion[];
+extern const char kPrefsChannelOnSlotPrefix[];
+extern const char kPrefsSystemUpdatedMarker[];
+extern const char kPrefsTargetVersionAttempt[];
+extern const char kPrefsTargetVersionInstalledFrom[];
+extern const char kPrefsTargetVersionUniqueId[];
+extern const char kPrefsTotalBytesDownloaded[];
+extern const char kPrefsUpdateCheckCount[];
+extern const char kPrefsUpdateCheckResponseHash[];
+extern const char kPrefsUpdateCompletedBootTime[];
+extern const char kPrefsUpdateCompletedOnBootId[];
+extern const char kPrefsUpdateDurationUptime[];
+extern const char kPrefsUpdateFirstSeenAt[];
+extern const char kPrefsUpdateOverCellularPermission[];
+extern const char kPrefsUpdateServerCertificate[];
+extern const char kPrefsUpdateStateNextDataLength[];
+extern const char kPrefsUpdateStateNextDataOffset[];
+extern const char kPrefsUpdateStateNextOperation[];
+extern const char kPrefsUpdateStateSHA256Context[];
+extern const char kPrefsUpdateStateSignatureBlob[];
+extern const char kPrefsUpdateStateSignedSHA256Context[];
+extern const char kPrefsUpdateTimestampStart[];
+extern const char kPrefsUrlSwitchCount[];
+extern const char kPrefsWallClockWaitPeriod[];
+
+// A download source is any combination of protocol and server (that's of
+// interest to us when looking at UMA metrics) using which we may download
+// the payload.
+typedef enum {
+  kDownloadSourceHttpsServer,  // UMA Binary representation: 0001
+  kDownloadSourceHttpServer,   // UMA Binary representation: 0010
+  kDownloadSourceHttpPeer,     // UMA Binary representation: 0100
+
+  // Note: Add new sources only above this line.
+  kNumDownloadSources
+} DownloadSource;
+
+// A payload can be a Full or Delta payload. In some cases, a Full payload is
+// used even when a Delta payload was available for the update, called here
+// ForcedFull. The PayloadType enum is only used to send UMA metrics about the
+// successfully applied payload.
+typedef enum {
+  kPayloadTypeFull,
+  kPayloadTypeDelta,
+  kPayloadTypeForcedFull,
+
+  // Note: Add new payload types only above this line.
+  kNumPayloadTypes
+} PayloadType;
+
+// Maximum number of times we'll allow using p2p for the same update payload.
+const int kMaxP2PAttempts = 10;
+
+// Maximum wallclock time we allow attempting to update using p2p for
+// the same update payload - five days.
+const int kMaxP2PAttemptTimeSeconds = 5 * 24 * 60 * 60;
+
+// The maximum amount of time to spend waiting for p2p-client(1) to
+// return while waiting in line to use the LAN - six hours.
+const int kMaxP2PNetworkWaitTimeSeconds = 6 * 60 * 60;
+
+// The maximum number of payload files to keep in /var/cache/p2p.
+const int kMaxP2PFilesToKeep = 3;
+
+// The maximum number of days to keep a p2p file;
+const int kMaxP2PFileAgeDays = 5;
+
+// The default number of UMA buckets for metrics.
+const int kNumDefaultUmaBuckets = 50;
+
+// General constants
+const int kNumBytesInOneMiB = 1024 * 1024;
+
+// Number of redirects allowed when downloading.
+const int kDownloadMaxRedirects = 10;
+
+// The minimum average speed that downloads must sustain...
+//
+// This is set low because some devices may have very poor
+// connectivity and we want to make as much forward progress as
+// possible. For p2p this is high (25 kB/second) since we can assume
+// high bandwidth (same LAN) and we want to fail fast.
+const int kDownloadLowSpeedLimitBps = 1;
+const int kDownloadP2PLowSpeedLimitBps = 25 * 1000;
+
+// ... measured over this period.
+//
+// For non-official builds (e.g. typically built on a developer's
+// workstation and served via devserver) bump this since it takes time
+// for the workstation to generate the payload. For p2p, make this
+// relatively low since we want to fail fast.
+const int kDownloadLowSpeedTimeSeconds = 90;
+const int kDownloadDevModeLowSpeedTimeSeconds = 180;
+const int kDownloadP2PLowSpeedTimeSeconds = 60;
+
+// The maximum amount of HTTP server reconnect attempts.
+//
+// This is set high in order to maximize the attempt's chance of
+// succeeding. When using p2p, this is low in order to fail fast.
+const int kDownloadMaxRetryCount = 20;
+const int kDownloadMaxRetryCountOobeNotComplete = 3;
+const int kDownloadP2PMaxRetryCount = 5;
+
+// The connect timeout, in seconds.
+//
+// This is set high because some devices may have very poor
+// connectivity and we may be using HTTPS which involves complicated
+// multi-roundtrip setup. For p2p, this is set low because we can
+// the server is on the same LAN and we want to fail fast.
+const int kDownloadConnectTimeoutSeconds = 30;
+const int kDownloadP2PConnectTimeoutSeconds = 5;
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_CONSTANTS_H_
diff --git a/common/error_code.h b/common/error_code.h
new file mode 100644
index 0000000..2bbdcfa
--- /dev/null
+++ b/common/error_code.h
@@ -0,0 +1,135 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_ERROR_CODE_H_
+#define UPDATE_ENGINE_COMMON_ERROR_CODE_H_
+
+#include <ostream>  // NOLINT(readability/streams)
+
+namespace chromeos_update_engine {
+
+// Action exit codes.
+enum class ErrorCode : int {
+  kSuccess = 0,
+  kError = 1,
+  kOmahaRequestError = 2,
+  kOmahaResponseHandlerError = 3,
+  kFilesystemCopierError = 4,
+  kPostinstallRunnerError = 5,
+  kPayloadMismatchedType = 6,
+  kInstallDeviceOpenError = 7,
+  kKernelDeviceOpenError = 8,
+  kDownloadTransferError = 9,
+  kPayloadHashMismatchError = 10,
+  kPayloadSizeMismatchError = 11,
+  kDownloadPayloadVerificationError = 12,
+  kDownloadNewPartitionInfoError = 13,
+  kDownloadWriteError = 14,
+  kNewRootfsVerificationError = 15,
+  kNewKernelVerificationError = 16,
+  kSignedDeltaPayloadExpectedError = 17,
+  kDownloadPayloadPubKeyVerificationError = 18,
+  kPostinstallBootedFromFirmwareB = 19,
+  kDownloadStateInitializationError = 20,
+  kDownloadInvalidMetadataMagicString = 21,
+  kDownloadSignatureMissingInManifest = 22,
+  kDownloadManifestParseError = 23,
+  kDownloadMetadataSignatureError = 24,
+  kDownloadMetadataSignatureVerificationError = 25,
+  kDownloadMetadataSignatureMismatch = 26,
+  kDownloadOperationHashVerificationError = 27,
+  kDownloadOperationExecutionError = 28,
+  kDownloadOperationHashMismatch = 29,
+  kOmahaRequestEmptyResponseError = 30,
+  kOmahaRequestXMLParseError = 31,
+  kDownloadInvalidMetadataSize = 32,
+  kDownloadInvalidMetadataSignature = 33,
+  kOmahaResponseInvalid = 34,
+  kOmahaUpdateIgnoredPerPolicy = 35,
+  kOmahaUpdateDeferredPerPolicy = 36,
+  kOmahaErrorInHTTPResponse = 37,
+  kDownloadOperationHashMissingError = 38,
+  kDownloadMetadataSignatureMissingError = 39,
+  kOmahaUpdateDeferredForBackoff = 40,
+  kPostinstallPowerwashError = 41,
+  kUpdateCanceledByChannelChange = 42,
+  kPostinstallFirmwareRONotUpdatable = 43,
+  kUnsupportedMajorPayloadVersion = 44,
+  kUnsupportedMinorPayloadVersion = 45,
+  kOmahaRequestXMLHasEntityDecl = 46,
+  kFilesystemVerifierError = 47,
+
+  // VERY IMPORTANT! When adding new error codes:
+  //
+  // 1) Update tools/metrics/histograms/histograms.xml in Chrome.
+  //
+  // 2) Update the assorted switch statements in update_engine which won't
+  //    build until this case is added.
+
+  // Any code above this is sent to both Omaha and UMA as-is, except
+  // kOmahaErrorInHTTPResponse (see error code 2000 for more details).
+  // Codes/flags below this line is sent only to Omaha and not to UMA.
+
+  // kUmaReportedMax is not an error code per se, it's just the count
+  // of the number of enums above.  Add any new errors above this line if you
+  // want them to show up on UMA. Stuff below this line will not be sent to UMA
+  // but is used for other errors that are sent to Omaha. We don't assign any
+  // particular value for this enum so that it's just one more than the last
+  // one above and thus always represents the correct count of UMA metrics
+  // buckets, even when new enums are added above this line in future. See
+  // metrics::ReportUpdateAttemptMetrics() on how this enum is used.
+  kUmaReportedMax,
+
+  // use the 2xxx range to encode HTTP errors. These errors are available in
+  // Dremel with the individual granularity. But for UMA purposes, all these
+  // errors are aggregated into one: kOmahaErrorInHTTPResponse.
+  kOmahaRequestHTTPResponseBase = 2000,  // + HTTP response code
+
+  // TODO(jaysri): Move out all the bit masks into separate constants
+  // outside the enum as part of fixing bug 34369.
+  // Bit flags. Remember to update the mask below for new bits.
+
+  // Set if boot mode not normal.
+  // TODO(garnold) This is very debatable value to use, knowing that the
+  // underlying type is a signed int (often, 32-bit). However, at this point
+  // there are parts of the ecosystem that expect this to be a negative value,
+  // so we preserve this semantics. This should be reconsidered if/when we
+  // modify the implementation of ErrorCode into a properly encapsulated class.
+  kDevModeFlag = 1 << 31,
+
+  // Set if resuming an interruped update.
+  kResumedFlag = 1 << 30,
+
+  // Set if using a dev/test image as opposed to an MP-signed image.
+  kTestImageFlag = 1 << 29,
+
+  // Set if using devserver or Omaha sandbox (using crosh autest).
+  kTestOmahaUrlFlag = 1 << 28,
+
+  // Mask that indicates bit positions that are used to indicate special flags
+  // that are embedded in the error code to provide additional context about
+  // the system in which the error was encountered.
+  kSpecialFlags = (kDevModeFlag | kResumedFlag | kTestImageFlag |
+                   kTestOmahaUrlFlag)
+};
+
+inline std::ostream& operator<<(std::ostream& os, ErrorCode val) {
+  return os << static_cast<int>(val);
+}
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_ERROR_CODE_H_
diff --git a/common/fake_boot_control.h b/common/fake_boot_control.h
new file mode 100644
index 0000000..5c6c160
--- /dev/null
+++ b/common/fake_boot_control.h
@@ -0,0 +1,112 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_FAKE_BOOT_CONTROL_H_
+#define UPDATE_ENGINE_COMMON_FAKE_BOOT_CONTROL_H_
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/boot_control_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a fake bootloader control interface used for testing.
+class FakeBootControl : public BootControlInterface {
+ public:
+  FakeBootControl() {
+    SetNumSlots(num_slots_);
+    // The current slot should be bootable.
+    is_bootable_[current_slot_] = true;
+  }
+
+  // BootControlInterface overrides.
+  unsigned int GetNumSlots() const override { return num_slots_; }
+  BootControlInterface::Slot GetCurrentSlot() const override {
+    return current_slot_;
+  }
+
+  bool GetPartitionDevice(const std::string& partition_name,
+                          BootControlInterface::Slot slot,
+                          std::string* device) const override {
+    if (slot >= num_slots_)
+      return false;
+    auto part_it = devices_[slot].find(partition_name);
+    if (part_it == devices_[slot].end())
+      return false;
+    *device = part_it->second;
+    return true;
+  }
+
+  bool IsSlotBootable(BootControlInterface::Slot slot) const override {
+    return slot < num_slots_ && is_bootable_[slot];
+  }
+
+  bool MarkSlotUnbootable(BootControlInterface::Slot slot) override {
+    if (slot >= num_slots_)
+      return false;
+    is_bootable_[slot] = false;
+    return true;
+  }
+
+  bool SetActiveBootSlot(Slot slot) override { return true; }
+
+  bool MarkBootSuccessfulAsync(base::Callback<void(bool)> callback) override {
+    // We run the callback directly from here to avoid having to setup a message
+    // loop in the test environment.
+    callback.Run(true);
+    return true;
+  }
+
+  // Setters
+  void SetNumSlots(unsigned int num_slots) {
+    num_slots_ = num_slots;
+    is_bootable_.resize(num_slots_, false);
+    devices_.resize(num_slots_);
+  }
+
+  void SetCurrentSlot(BootControlInterface::Slot slot) {
+    current_slot_ = slot;
+  }
+
+  void SetPartitionDevice(const std::string partition_name,
+                          BootControlInterface::Slot slot,
+                          const std::string device) {
+    DCHECK(slot < num_slots_);
+    devices_[slot][partition_name] = device;
+  }
+
+  void SetSlotBootable(BootControlInterface::Slot slot, bool bootable) {
+    DCHECK(slot < num_slots_);
+    is_bootable_[slot] = bootable;
+  }
+
+ private:
+  BootControlInterface::Slot num_slots_{2};
+  BootControlInterface::Slot current_slot_{0};
+
+  std::vector<bool> is_bootable_;
+  std::vector<std::map<std::string, std::string>> devices_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeBootControl);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_FAKE_BOOT_CONTROL_H_
diff --git a/common/fake_clock.h b/common/fake_clock.h
new file mode 100644
index 0000000..3d3bad8
--- /dev/null
+++ b/common/fake_clock.h
@@ -0,0 +1,63 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_FAKE_CLOCK_H_
+#define UPDATE_ENGINE_COMMON_FAKE_CLOCK_H_
+
+#include "update_engine/common/clock_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a clock that can be made to tell any time you want.
+class FakeClock : public ClockInterface {
+ public:
+  FakeClock() {}
+
+  base::Time GetWallclockTime() override {
+    return wallclock_time_;
+  }
+
+  base::Time GetMonotonicTime() override {
+    return monotonic_time_;
+  }
+
+  base::Time GetBootTime() override {
+    return boot_time_;
+  }
+
+  void SetWallclockTime(const base::Time &time) {
+    wallclock_time_ = time;
+  }
+
+  void SetMonotonicTime(const base::Time &time) {
+    monotonic_time_ = time;
+  }
+
+  void SetBootTime(const base::Time &time) {
+    boot_time_ = time;
+  }
+
+ private:
+  base::Time wallclock_time_;
+  base::Time monotonic_time_;
+  base::Time boot_time_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeClock);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_FAKE_CLOCK_H_
diff --git a/common/fake_hardware.h b/common/fake_hardware.h
new file mode 100644
index 0000000..23d6498
--- /dev/null
+++ b/common/fake_hardware.h
@@ -0,0 +1,124 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_FAKE_HARDWARE_H_
+#define UPDATE_ENGINE_COMMON_FAKE_HARDWARE_H_
+
+#include <map>
+#include <string>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/hardware_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a fake hardware interface used for testing.
+class FakeHardware : public HardwareInterface {
+ public:
+  // Value used to signal that the powerwash_count file is not present. When
+  // this value is used in SetPowerwashCount(), GetPowerwashCount() will return
+  // false.
+  static const int kPowerwashCountNotSet = -1;
+
+  FakeHardware()
+      : is_official_build_(true),
+        is_normal_boot_mode_(true),
+        is_oobe_complete_(false),
+        hardware_class_("Fake HWID BLAH-1234"),
+        firmware_version_("Fake Firmware v1.0.1"),
+        ec_version_("Fake EC v1.0a"),
+        powerwash_count_(kPowerwashCountNotSet) {}
+
+  // HardwareInterface methods.
+  bool IsOfficialBuild() const override { return is_official_build_; }
+
+  bool IsNormalBootMode() const override { return is_normal_boot_mode_; }
+
+  bool IsOOBEComplete(base::Time* out_time_of_oobe) const override {
+    if (out_time_of_oobe != nullptr)
+      *out_time_of_oobe = oobe_timestamp_;
+    return is_oobe_complete_;
+  }
+
+  std::string GetHardwareClass() const override { return hardware_class_; }
+
+  std::string GetFirmwareVersion() const override { return firmware_version_; }
+
+  std::string GetECVersion() const override { return ec_version_; }
+
+  int GetPowerwashCount() const override { return powerwash_count_; }
+
+  bool GetNonVolatileDirectory(base::FilePath* path) const override {
+    return false;
+  }
+
+  bool GetPowerwashSafeDirectory(base::FilePath* path) const override {
+    return false;
+  }
+
+  // Setters
+  void SetIsOfficialBuild(bool is_official_build) {
+    is_official_build_ = is_official_build;
+  }
+
+  void SetIsNormalBootMode(bool is_normal_boot_mode) {
+    is_normal_boot_mode_ = is_normal_boot_mode;
+  }
+
+  // Sets the IsOOBEComplete to True with the given timestamp.
+  void SetIsOOBEComplete(base::Time oobe_timestamp) {
+    is_oobe_complete_ = true;
+    oobe_timestamp_ = oobe_timestamp;
+  }
+
+  // Sets the IsOOBEComplete to False.
+  void UnsetIsOOBEComplete() {
+    is_oobe_complete_ = false;
+  }
+
+  void SetHardwareClass(std::string hardware_class) {
+    hardware_class_ = hardware_class;
+  }
+
+  void SetFirmwareVersion(std::string firmware_version) {
+    firmware_version_ = firmware_version;
+  }
+
+  void SetECVersion(std::string ec_version) {
+    ec_version_ = ec_version;
+  }
+
+  void SetPowerwashCount(int powerwash_count) {
+    powerwash_count_ = powerwash_count;
+  }
+
+ private:
+  bool is_official_build_;
+  bool is_normal_boot_mode_;
+  bool is_oobe_complete_;
+  base::Time oobe_timestamp_;
+  std::string hardware_class_;
+  std::string firmware_version_;
+  std::string ec_version_;
+  int powerwash_count_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeHardware);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_FAKE_HARDWARE_H_
diff --git a/common/fake_prefs.cc b/common/fake_prefs.cc
new file mode 100644
index 0000000..5a0a3af
--- /dev/null
+++ b/common/fake_prefs.cc
@@ -0,0 +1,168 @@
+//
+// Copyright (C) 2014 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 "update_engine/common/fake_prefs.h"
+
+#include <algorithm>
+
+#include <gtest/gtest.h>
+
+using std::string;
+
+using chromeos_update_engine::FakePrefs;
+
+namespace {
+
+void CheckNotNull(const string& key, void* ptr) {
+  EXPECT_NE(nullptr, ptr)
+      << "Called Get*() for key \"" << key << "\" with a null parameter.";
+}
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+FakePrefs::~FakePrefs() {
+  EXPECT_TRUE(observers_.empty());
+}
+
+// Compile-time type-dependent constants definitions.
+template<>
+FakePrefs::PrefType const FakePrefs::PrefConsts<string>::type =
+    FakePrefs::PrefType::kString;
+template<>
+string FakePrefs::PrefValue::* const  // NOLINT(runtime/string), not static str.
+    FakePrefs::PrefConsts<string>::member = &FakePrefs::PrefValue::as_str;
+
+template<>
+FakePrefs::PrefType const FakePrefs::PrefConsts<int64_t>::type =
+    FakePrefs::PrefType::kInt64;
+template<>
+int64_t FakePrefs::PrefValue::* const FakePrefs::PrefConsts<int64_t>::member =
+    &FakePrefs::PrefValue::as_int64;
+
+template<>
+FakePrefs::PrefType const FakePrefs::PrefConsts<bool>::type =
+    FakePrefs::PrefType::kBool;
+template<>
+bool FakePrefs::PrefValue::* const FakePrefs::PrefConsts<bool>::member =
+    &FakePrefs::PrefValue::as_bool;
+
+bool FakePrefs::GetString(const string& key, string* value) const {
+  return GetValue(key, value);
+}
+
+bool FakePrefs::SetString(const string& key, const string& value) {
+  SetValue(key, value);
+  return true;
+}
+
+bool FakePrefs::GetInt64(const string& key, int64_t* value) const {
+  return GetValue(key, value);
+}
+
+bool FakePrefs::SetInt64(const string& key, const int64_t value) {
+  SetValue(key, value);
+  return true;
+}
+
+bool FakePrefs::GetBoolean(const string& key, bool* value) const {
+  return GetValue(key, value);
+}
+
+bool FakePrefs::SetBoolean(const string& key, const bool value) {
+  SetValue(key, value);
+  return true;
+}
+
+bool FakePrefs::Exists(const string& key) const {
+  return values_.find(key) != values_.end();
+}
+
+bool FakePrefs::Delete(const string& key) {
+  if (values_.find(key) == values_.end())
+    return false;
+  values_.erase(key);
+  const auto observers_for_key = observers_.find(key);
+  if (observers_for_key != observers_.end()) {
+    std::vector<ObserverInterface*> copy_observers(observers_for_key->second);
+    for (ObserverInterface* observer : copy_observers)
+      observer->OnPrefDeleted(key);
+  }
+  return true;
+}
+
+string FakePrefs::GetTypeName(PrefType type) {
+  switch (type) {
+    case PrefType::kString:
+      return "string";
+    case PrefType::kInt64:
+      return "int64_t";
+    case PrefType::kBool:
+      return "bool";
+  }
+  return "Unknown";
+}
+
+void FakePrefs::CheckKeyType(const string& key, PrefType type) const {
+  auto it = values_.find(key);
+  EXPECT_TRUE(it == values_.end() || it->second.type == type)
+      << "Key \"" << key << "\" if defined as " << GetTypeName(it->second.type)
+      << " but is accessed as a " << GetTypeName(type);
+}
+
+template<typename T>
+void FakePrefs::SetValue(const string& key, const T& value) {
+  CheckKeyType(key, PrefConsts<T>::type);
+  values_[key].type = PrefConsts<T>::type;
+  values_[key].value.*(PrefConsts<T>::member) = value;
+  const auto observers_for_key = observers_.find(key);
+  if (observers_for_key != observers_.end()) {
+    std::vector<ObserverInterface*> copy_observers(observers_for_key->second);
+    for (ObserverInterface* observer : copy_observers)
+      observer->OnPrefSet(key);
+  }
+}
+
+template<typename T>
+bool FakePrefs::GetValue(const string& key, T* value) const {
+  CheckKeyType(key, PrefConsts<T>::type);
+  auto it = values_.find(key);
+  if (it == values_.end())
+    return false;
+  CheckNotNull(key, value);
+  *value = it->second.value.*(PrefConsts<T>::member);
+  return true;
+}
+
+void FakePrefs::AddObserver(const string& key, ObserverInterface* observer) {
+  observers_[key].push_back(observer);
+}
+
+void FakePrefs::RemoveObserver(const string& key, ObserverInterface* observer) {
+  std::vector<ObserverInterface*>& observers_for_key = observers_[key];
+  auto observer_it =
+      std::find(observers_for_key.begin(), observers_for_key.end(), observer);
+  EXPECT_NE(observer_it, observers_for_key.end())
+      << "Trying to remove an observer instance not watching the key "
+      << key;
+  if (observer_it != observers_for_key.end())
+    observers_for_key.erase(observer_it);
+  if (observers_for_key.empty())
+    observers_.erase(key);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/fake_prefs.h b/common/fake_prefs.h
new file mode 100644
index 0000000..d194060
--- /dev/null
+++ b/common/fake_prefs.h
@@ -0,0 +1,113 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_FAKE_PREFS_H_
+#define UPDATE_ENGINE_COMMON_FAKE_PREFS_H_
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/common/prefs_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a fake preference store by storing the value associated with
+// a key in a std::map, suitable for testing. It doesn't allow to set a value on
+// a key with a different type than the previously set type. This enforces the
+// type of a given key to be fixed. Also the class checks that the Get*()
+// methods aren't called on a key set with a different type.
+
+class FakePrefs : public PrefsInterface {
+ public:
+  FakePrefs() = default;
+  ~FakePrefs();
+
+  // PrefsInterface methods.
+  bool GetString(const std::string& key, std::string* value) const override;
+  bool SetString(const std::string& key, const std::string& value) override;
+  bool GetInt64(const std::string& key, int64_t* value) const override;
+  bool SetInt64(const std::string& key, const int64_t value) override;
+  bool GetBoolean(const std::string& key, bool* value) const override;
+  bool SetBoolean(const std::string& key, const bool value) override;
+
+  bool Exists(const std::string& key) const override;
+  bool Delete(const std::string& key) override;
+
+  void AddObserver(const std::string& key,
+                   ObserverInterface* observer) override;
+  void RemoveObserver(const std::string& key,
+                      ObserverInterface* observer) override;
+
+ private:
+  enum class PrefType {
+    kString,
+    kInt64,
+    kBool,
+  };
+  struct PrefValue {
+    std::string as_str;
+    int64_t as_int64;
+    bool as_bool;
+  };
+
+  struct PrefTypeValue {
+    PrefType type;
+    PrefValue value;
+  };
+
+  // Class to store compile-time type-dependent constants.
+  template<typename T>
+  class PrefConsts {
+   public:
+    // The PrefType associated with T.
+    static FakePrefs::PrefType const type;
+
+    // The data member pointer to PrefValue associated with T.
+    static T FakePrefs::PrefValue::* const member;
+  };
+
+  // Returns a string representation of the PrefType useful for logging.
+  static std::string GetTypeName(PrefType type);
+
+  // Checks that the |key| is either not present or has the given |type|.
+  void CheckKeyType(const std::string& key, PrefType type) const;
+
+  // Helper function to set a value of the passed |key|. It sets the type based
+  // on the template parameter T.
+  template<typename T>
+  void SetValue(const std::string& key, const T& value);
+
+  // Helper function to get a value from the map checking for invalid calls.
+  // The function fails the test if you attempt to read a value  defined as a
+  // different type. Returns whether the get succeeded.
+  template<typename T>
+  bool GetValue(const std::string& key, T* value) const;
+
+  // Container for all the key/value pairs.
+  std::map<std::string, PrefTypeValue> values_;
+
+  // The registered observers watching for changes.
+  std::map<std::string, std::vector<ObserverInterface*>> observers_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakePrefs);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_FAKE_PREFS_H_
diff --git a/common/hardware.h b/common/hardware.h
new file mode 100644
index 0000000..f1365e0
--- /dev/null
+++ b/common/hardware.h
@@ -0,0 +1,34 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_HARDWARE_H_
+#define UPDATE_ENGINE_COMMON_HARDWARE_H_
+
+#include <memory>
+
+#include "update_engine/common/hardware_interface.h"
+
+namespace chromeos_update_engine {
+namespace hardware {
+
+// The real HardwareInterface is platform-specific. This factory function
+// creates a new HardwareInterface instance for the current platform.
+std::unique_ptr<HardwareInterface> CreateHardware();
+
+}  // namespace hardware
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HARDWARE_H_
diff --git a/common/hardware_interface.h b/common/hardware_interface.h
new file mode 100644
index 0000000..17ce694
--- /dev/null
+++ b/common/hardware_interface.h
@@ -0,0 +1,81 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_HARDWARE_INTERFACE_H_
+#define UPDATE_ENGINE_COMMON_HARDWARE_INTERFACE_H_
+
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/time/time.h>
+
+namespace chromeos_update_engine {
+
+// The hardware interface allows access to the crossystem exposed properties,
+// such as the firmware version, hwid, verified boot mode.
+// These stateless functions are tied together in this interface to facilitate
+// unit testing.
+class HardwareInterface {
+ public:
+  virtual ~HardwareInterface() {}
+
+  // Returns whether this is an official build. Official build means that the
+  // server maintains and updates the build, so update_engine should run and
+  // periodically check for updates.
+  virtual bool IsOfficialBuild() const = 0;
+
+  // Returns true if the boot mode is normal or if it's unable to
+  // determine the boot mode. Returns false if the boot mode is
+  // developer. A dev-mode boot will allow the user to access developer-only
+  // features.
+  virtual bool IsNormalBootMode() const = 0;
+
+  // Returns true if the OOBE process has been completed and EULA accepted,
+  // False otherwise. If True is returned, and |out_time_of_oobe| isn't null,
+  // the time-stamp of when OOBE happened is stored at |out_time_of_oobe|.
+  virtual bool IsOOBEComplete(base::Time* out_time_of_oobe) const = 0;
+
+  // Returns the HWID or an empty string on error.
+  virtual std::string GetHardwareClass() const = 0;
+
+  // Returns the firmware version or an empty string if the system is
+  // not running chrome os firmware.
+  virtual std::string GetFirmwareVersion() const = 0;
+
+  // Returns the ec version or an empty string if the system is not
+  // running a custom chrome os ec.
+  virtual std::string GetECVersion() const = 0;
+
+  // Returns the powerwash_count from the stateful. If the file is not found
+  // or is invalid, returns -1. Brand new machines out of the factory or after
+  // recovery don't have this value set.
+  virtual int GetPowerwashCount() const = 0;
+
+  // Store in |path| the path to a non-volatile directory (persisted across
+  // reboots) available for this daemon. In case of an error, such as no
+  // directory available, returns false.
+  virtual bool GetNonVolatileDirectory(base::FilePath* path) const = 0;
+
+  // Store in |path| the path to a non-volatile directory persisted across
+  // powerwash cycles. In case of an error, such as no directory available,
+  // returns false.
+  virtual bool GetPowerwashSafeDirectory(base::FilePath* path) const = 0;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HARDWARE_INTERFACE_H_
diff --git a/common/hash_calculator.cc b/common/hash_calculator.cc
new file mode 100644
index 0000000..de6e0f9
--- /dev/null
+++ b/common/hash_calculator.cc
@@ -0,0 +1,143 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/hash_calculator.h"
+
+#include <fcntl.h>
+
+#include <base/logging.h>
+#include <base/posix/eintr_wrapper.h>
+#include <brillo/data_encoding.h>
+
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+HashCalculator::HashCalculator() : valid_(false) {
+  valid_ = (SHA256_Init(&ctx_) == 1);
+  LOG_IF(ERROR, !valid_) << "SHA256_Init failed";
+}
+
+// Update is called with all of the data that should be hashed in order.
+// Mostly just passes the data through to OpenSSL's SHA256_Update()
+bool HashCalculator::Update(const void* data, size_t length) {
+  TEST_AND_RETURN_FALSE(valid_);
+  TEST_AND_RETURN_FALSE(hash_.empty());
+  static_assert(sizeof(size_t) <= sizeof(unsigned long),  // NOLINT(runtime/int)
+                "length param may be truncated in SHA256_Update");
+  TEST_AND_RETURN_FALSE(SHA256_Update(&ctx_, data, length) == 1);
+  return true;
+}
+
+off_t HashCalculator::UpdateFile(const string& name, off_t length) {
+  int fd = HANDLE_EINTR(open(name.c_str(), O_RDONLY));
+  if (fd < 0) {
+    return -1;
+  }
+
+  const int kBufferSize = 128 * 1024;  // 128 KiB
+  brillo::Blob buffer(kBufferSize);
+  off_t bytes_processed = 0;
+  while (length < 0 || bytes_processed < length) {
+    off_t bytes_to_read = buffer.size();
+    if (length >= 0 && bytes_to_read > length - bytes_processed) {
+      bytes_to_read = length - bytes_processed;
+    }
+    ssize_t rc = HANDLE_EINTR(read(fd, buffer.data(), bytes_to_read));
+    if (rc == 0) {  // EOF
+      break;
+    }
+    if (rc < 0 || !Update(buffer.data(), rc)) {
+      bytes_processed = -1;
+      break;
+    }
+    bytes_processed += rc;
+  }
+  IGNORE_EINTR(close(fd));
+  return bytes_processed;
+}
+
+// Call Finalize() when all data has been passed in. This mostly just
+// calls OpenSSL's SHA256_Final() and then base64 encodes the hash.
+bool HashCalculator::Finalize() {
+  TEST_AND_RETURN_FALSE(hash_.empty());
+  TEST_AND_RETURN_FALSE(raw_hash_.empty());
+  raw_hash_.resize(SHA256_DIGEST_LENGTH);
+  TEST_AND_RETURN_FALSE(SHA256_Final(raw_hash_.data(), &ctx_) == 1);
+
+  // Convert raw_hash_ to base64 encoding and store it in hash_.
+  hash_ = brillo::data_encoding::Base64Encode(raw_hash_.data(),
+                                              raw_hash_.size());
+  return true;
+}
+
+bool HashCalculator::RawHashOfBytes(const void* data,
+                                    size_t length,
+                                    brillo::Blob* out_hash) {
+  HashCalculator calc;
+  TEST_AND_RETURN_FALSE(calc.Update(data, length));
+  TEST_AND_RETURN_FALSE(calc.Finalize());
+  *out_hash = calc.raw_hash();
+  return true;
+}
+
+bool HashCalculator::RawHashOfData(const brillo::Blob& data,
+                                   brillo::Blob* out_hash) {
+  return RawHashOfBytes(data.data(), data.size(), out_hash);
+}
+
+off_t HashCalculator::RawHashOfFile(const string& name, off_t length,
+                                    brillo::Blob* out_hash) {
+  HashCalculator calc;
+  off_t res = calc.UpdateFile(name, length);
+  if (res < 0) {
+    return res;
+  }
+  if (!calc.Finalize()) {
+    return -1;
+  }
+  *out_hash = calc.raw_hash();
+  return res;
+}
+
+string HashCalculator::HashOfBytes(const void* data, size_t length) {
+  HashCalculator calc;
+  calc.Update(data, length);
+  calc.Finalize();
+  return calc.hash();
+}
+
+string HashCalculator::HashOfString(const string& str) {
+  return HashOfBytes(str.data(), str.size());
+}
+
+string HashCalculator::HashOfData(const brillo::Blob& data) {
+  return HashOfBytes(data.data(), data.size());
+}
+
+string HashCalculator::GetContext() const {
+  return string(reinterpret_cast<const char*>(&ctx_), sizeof(ctx_));
+}
+
+bool HashCalculator::SetContext(const string& context) {
+  TEST_AND_RETURN_FALSE(context.size() == sizeof(ctx_));
+  memcpy(&ctx_, context.data(), sizeof(ctx_));
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/hash_calculator.h b/common/hash_calculator.h
new file mode 100644
index 0000000..f749585
--- /dev/null
+++ b/common/hash_calculator.h
@@ -0,0 +1,107 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_HASH_CALCULATOR_H_
+#define UPDATE_ENGINE_COMMON_HASH_CALCULATOR_H_
+
+#include <openssl/sha.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+// Omaha uses base64 encoded SHA-256 as the hash. This class provides a simple
+// wrapper around OpenSSL providing such a formatted hash of data passed in.
+// The methods of this class must be called in a very specific order: First the
+// ctor (of course), then 0 or more calls to Update(), then Finalize(), then 0
+// or more calls to hash().
+
+namespace chromeos_update_engine {
+
+class HashCalculator {
+ public:
+  HashCalculator();
+
+  // Update is called with all of the data that should be hashed in order.
+  // Update will read |length| bytes of |data|.
+  // Returns true on success.
+  bool Update(const void* data, size_t length);
+
+  // Updates the hash with up to |length| bytes of data from |file|. If |length|
+  // is negative, reads in and updates with the whole file. Returns the number
+  // of bytes that the hash was updated with, or -1 on error.
+  off_t UpdateFile(const std::string& name, off_t length);
+
+  // Call Finalize() when all data has been passed in. This method tells
+  // OpenSSl that no more data will come in and base64 encodes the resulting
+  // hash.
+  // Returns true on success.
+  bool Finalize();
+
+  // Gets the hash. Finalize() must have been called.
+  const std::string& hash() const {
+    DCHECK(!hash_.empty()) << "Call Finalize() first";
+    return hash_;
+  }
+
+  const brillo::Blob& raw_hash() const {
+    DCHECK(!raw_hash_.empty()) << "Call Finalize() first";
+    return raw_hash_;
+  }
+
+  // Gets the current hash context. Note that the string will contain binary
+  // data (including \0 characters).
+  std::string GetContext() const;
+
+  // Sets the current hash context. |context| must the string returned by a
+  // previous HashCalculator::GetContext method call. Returns true on success,
+  // and false otherwise.
+  bool SetContext(const std::string& context);
+
+  static bool RawHashOfBytes(const void* data,
+                             size_t length,
+                             brillo::Blob* out_hash);
+  static bool RawHashOfData(const brillo::Blob& data,
+                            brillo::Blob* out_hash);
+  static off_t RawHashOfFile(const std::string& name, off_t length,
+                             brillo::Blob* out_hash);
+
+  // Used by tests
+  static std::string HashOfBytes(const void* data, size_t length);
+  static std::string HashOfString(const std::string& str);
+  static std::string HashOfData(const brillo::Blob& data);
+
+ private:
+  // If non-empty, the final base64 encoded hash and the raw hash. Will only be
+  // set to non-empty when Finalize is called.
+  std::string hash_;
+  brillo::Blob raw_hash_;
+
+  // Init success
+  bool valid_;
+
+  // The hash state used by OpenSSL
+  SHA256_CTX ctx_;
+  DISALLOW_COPY_AND_ASSIGN(HashCalculator);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HASH_CALCULATOR_H_
diff --git a/common/hash_calculator_unittest.cc b/common/hash_calculator_unittest.cc
new file mode 100644
index 0000000..27dbc56
--- /dev/null
+++ b/common/hash_calculator_unittest.cc
@@ -0,0 +1,174 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/hash_calculator.h"
+
+#include <math.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/libcurl_http_fetcher.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+// Generated by running this on a linux shell:
+// $ echo -n hi | openssl dgst -sha256 -binary | openssl base64
+static const char kExpectedHash[] =
+    "j0NDRmSPa5bfid2pAcUXaxCm2Dlh3TwayItZstwyeqQ=";
+static const uint8_t kExpectedRawHash[] = {
+  0x8f, 0x43, 0x43, 0x46, 0x64, 0x8f, 0x6b, 0x96,
+  0xdf, 0x89, 0xdd, 0xa9, 0x01, 0xc5, 0x17, 0x6b,
+  0x10, 0xa6, 0xd8, 0x39, 0x61, 0xdd, 0x3c, 0x1a,
+  0xc8, 0x8b, 0x59, 0xb2, 0xdc, 0x32, 0x7a, 0xa4
+};
+
+class HashCalculatorTest : public ::testing::Test {
+ public:
+  HashCalculatorTest() {}
+};
+
+TEST_F(HashCalculatorTest, SimpleTest) {
+  HashCalculator calc;
+  calc.Update("hi", 2);
+  calc.Finalize();
+  EXPECT_EQ(kExpectedHash, calc.hash());
+  brillo::Blob raw_hash(std::begin(kExpectedRawHash),
+                        std::end(kExpectedRawHash));
+  EXPECT_TRUE(raw_hash == calc.raw_hash());
+}
+
+TEST_F(HashCalculatorTest, MultiUpdateTest) {
+  HashCalculator calc;
+  calc.Update("h", 1);
+  calc.Update("i", 1);
+  calc.Finalize();
+  EXPECT_EQ(kExpectedHash, calc.hash());
+  brillo::Blob raw_hash(std::begin(kExpectedRawHash),
+                        std::end(kExpectedRawHash));
+  EXPECT_TRUE(raw_hash == calc.raw_hash());
+}
+
+TEST_F(HashCalculatorTest, ContextTest) {
+  HashCalculator calc;
+  calc.Update("h", 1);
+  string calc_context = calc.GetContext();
+  calc.Finalize();
+  HashCalculator calc_next;
+  calc_next.SetContext(calc_context);
+  calc_next.Update("i", 1);
+  calc_next.Finalize();
+  EXPECT_EQ(kExpectedHash, calc_next.hash());
+  brillo::Blob raw_hash(std::begin(kExpectedRawHash),
+                        std::end(kExpectedRawHash));
+  EXPECT_TRUE(raw_hash == calc_next.raw_hash());
+}
+
+TEST_F(HashCalculatorTest, BigTest) {
+  HashCalculator calc;
+
+  int digit_count = 1;
+  int next_overflow = 10;
+  for (int i = 0; i < 1000000; i++) {
+    char buf[8];
+    if (i == next_overflow) {
+      next_overflow *= 10;
+      digit_count++;
+    }
+    ASSERT_EQ(digit_count, snprintf(buf, sizeof(buf), "%d", i)) << " i = " << i;
+    calc.Update(buf, strlen(buf));
+  }
+  calc.Finalize();
+
+  // Hash constant generated by running this on a linux shell:
+  // $ C=0
+  // $ while [ $C -lt 1000000 ]; do
+  //     echo -n $C
+  //     let C=C+1
+  //   done | openssl dgst -sha256 -binary | openssl base64
+  EXPECT_EQ("NZf8k6SPBkYMvhaX8YgzuMgbkLP1XZ+neM8K5wcSsf8=", calc.hash());
+}
+
+TEST_F(HashCalculatorTest, UpdateFileSimpleTest) {
+  string data_path;
+  ASSERT_TRUE(
+      utils::MakeTempFile("data.XXXXXX", &data_path, nullptr));
+  ScopedPathUnlinker data_path_unlinker(data_path);
+  ASSERT_TRUE(utils::WriteFile(data_path.c_str(), "hi", 2));
+
+  static const int kLengths[] = { -1, 2, 10 };
+  for (size_t i = 0; i < arraysize(kLengths); i++) {
+    HashCalculator calc;
+    EXPECT_EQ(2, calc.UpdateFile(data_path, kLengths[i]));
+    EXPECT_TRUE(calc.Finalize());
+    EXPECT_EQ(kExpectedHash, calc.hash());
+    brillo::Blob raw_hash(std::begin(kExpectedRawHash),
+                          std::end(kExpectedRawHash));
+    EXPECT_TRUE(raw_hash == calc.raw_hash());
+  }
+
+  HashCalculator calc;
+  EXPECT_EQ(0, calc.UpdateFile(data_path, 0));
+  EXPECT_EQ(1, calc.UpdateFile(data_path, 1));
+  EXPECT_TRUE(calc.Finalize());
+  // echo -n h | openssl dgst -sha256 -binary | openssl base64
+  EXPECT_EQ("qqlAJmTxpB9A67xSyZk+tmrrNmYClY/fqig7ceZNsSM=", calc.hash());
+}
+
+TEST_F(HashCalculatorTest, RawHashOfFileSimpleTest) {
+  string data_path;
+  ASSERT_TRUE(
+      utils::MakeTempFile("data.XXXXXX", &data_path, nullptr));
+  ScopedPathUnlinker data_path_unlinker(data_path);
+  ASSERT_TRUE(utils::WriteFile(data_path.c_str(), "hi", 2));
+
+  static const int kLengths[] = { -1, 2, 10 };
+  for (size_t i = 0; i < arraysize(kLengths); i++) {
+    brillo::Blob exp_raw_hash(std::begin(kExpectedRawHash),
+                              std::end(kExpectedRawHash));
+    brillo::Blob raw_hash;
+    EXPECT_EQ(2, HashCalculator::RawHashOfFile(data_path,
+                                               kLengths[i],
+                                               &raw_hash));
+    EXPECT_TRUE(exp_raw_hash == raw_hash);
+  }
+}
+
+TEST_F(HashCalculatorTest, UpdateFileNonexistentTest) {
+  HashCalculator calc;
+  EXPECT_EQ(-1, calc.UpdateFile("/some/non-existent/file", -1));
+}
+
+TEST_F(HashCalculatorTest, AbortTest) {
+  // Just make sure we don't crash and valgrind doesn't detect memory leaks
+  {
+    HashCalculator calc;
+  }
+  {
+    HashCalculator calc;
+    calc.Update("h", 1);
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/http_common.cc b/common/http_common.cc
new file mode 100644
index 0000000..7d98889
--- /dev/null
+++ b/common/http_common.cc
@@ -0,0 +1,86 @@
+//
+// Copyright (C) 2009 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.
+//
+
+// Implementation of common HTTP related functions.
+
+#include "update_engine/common/http_common.h"
+
+#include <base/macros.h>
+
+namespace chromeos_update_engine {
+
+const char *GetHttpResponseDescription(HttpResponseCode code) {
+  static const struct {
+    HttpResponseCode code;
+    const char* description;
+  } http_response_table[] = {
+    { kHttpResponseOk,                  "OK" },
+    { kHttpResponseCreated,             "Created" },
+    { kHttpResponseAccepted,            "Accepted" },
+    { kHttpResponseNonAuthInfo,         "Non-Authoritative Information" },
+    { kHttpResponseNoContent,           "No Content" },
+    { kHttpResponseResetContent,        "Reset Content" },
+    { kHttpResponsePartialContent,      "Partial Content" },
+    { kHttpResponseMultipleChoices,     "Multiple Choices" },
+    { kHttpResponseMovedPermanently,    "Moved Permanently" },
+    { kHttpResponseFound,               "Found" },
+    { kHttpResponseSeeOther,            "See Other" },
+    { kHttpResponseNotModified,         "Not Modified" },
+    { kHttpResponseUseProxy,            "Use Proxy" },
+    { kHttpResponseTempRedirect,        "Temporary Redirect" },
+    { kHttpResponseBadRequest,          "Bad Request" },
+    { kHttpResponseUnauth,              "Unauthorized" },
+    { kHttpResponseForbidden,           "Forbidden" },
+    { kHttpResponseNotFound,            "Not Found" },
+    { kHttpResponseRequestTimeout,      "Request Timeout" },
+    { kHttpResponseInternalServerError, "Internal Server Error" },
+    { kHttpResponseNotImplemented,      "Not Implemented" },
+    { kHttpResponseServiceUnavailable,  "Service Unavailable" },
+    { kHttpResponseVersionNotSupported, "HTTP Version Not Supported" },
+  };
+
+  bool is_found = false;
+  size_t i;
+  for (i = 0; i < arraysize(http_response_table); i++)
+    if ((is_found = (http_response_table[i].code == code)))
+      break;
+
+  return (is_found ? http_response_table[i].description : "(unsupported)");
+}
+
+HttpResponseCode StringToHttpResponseCode(const char *s) {
+  return static_cast<HttpResponseCode>(strtoul(s, nullptr, 10));
+}
+
+
+const char *GetHttpContentTypeString(HttpContentType type) {
+  static const struct {
+    HttpContentType type;
+    const char* str;
+  } http_content_type_table[] = {
+    { kHttpContentTypeTextXml, "text/xml" },
+  };
+
+  bool is_found = false;
+  size_t i;
+  for (i = 0; i < arraysize(http_content_type_table); i++)
+    if ((is_found = (http_content_type_table[i].type == type)))
+      break;
+
+  return (is_found ? http_content_type_table[i].str : nullptr);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/http_common.h b/common/http_common.h
new file mode 100644
index 0000000..041cad5
--- /dev/null
+++ b/common/http_common.h
@@ -0,0 +1,74 @@
+//
+// Copyright (C) 2009 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.
+//
+
+// This file contains general definitions used in implementing, testing and
+// emulating communication over HTTP.
+
+#ifndef UPDATE_ENGINE_COMMON_HTTP_COMMON_H_
+#define UPDATE_ENGINE_COMMON_HTTP_COMMON_H_
+
+#include <cstdlib>
+
+namespace chromeos_update_engine {
+
+// Enumeration type for HTTP response codes.
+enum HttpResponseCode {
+  kHttpResponseUndefined           = 0,
+  kHttpResponseOk                  = 200,
+  kHttpResponseCreated             = 201,
+  kHttpResponseAccepted            = 202,
+  kHttpResponseNonAuthInfo         = 203,
+  kHttpResponseNoContent           = 204,
+  kHttpResponseResetContent        = 205,
+  kHttpResponsePartialContent      = 206,
+  kHttpResponseMultipleChoices     = 300,
+  kHttpResponseMovedPermanently    = 301,
+  kHttpResponseFound               = 302,
+  kHttpResponseSeeOther            = 303,
+  kHttpResponseNotModified         = 304,
+  kHttpResponseUseProxy            = 305,
+  kHttpResponseTempRedirect        = 307,
+  kHttpResponseBadRequest          = 400,
+  kHttpResponseUnauth              = 401,
+  kHttpResponseForbidden           = 403,
+  kHttpResponseNotFound            = 404,
+  kHttpResponseRequestTimeout      = 408,
+  kHttpResponseReqRangeNotSat      = 416,
+  kHttpResponseInternalServerError = 500,
+  kHttpResponseNotImplemented      = 501,
+  kHttpResponseServiceUnavailable  = 503,
+  kHttpResponseVersionNotSupported = 505,
+};
+
+// Returns a standard HTTP status line string for a given response code.
+const char *GetHttpResponseDescription(HttpResponseCode code);
+
+// Converts a string beginning with an HTTP error code into numerical value.
+HttpResponseCode StringToHttpResponseCode(const char *s);
+
+
+// Enumeration type for HTTP Content-Type.
+enum HttpContentType {
+  kHttpContentTypeUnspecified = 0,
+  kHttpContentTypeTextXml,
+};
+
+// Returns a standard HTTP Content-Type string.
+const char *GetHttpContentTypeString(HttpContentType type);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HTTP_COMMON_H_
diff --git a/common/http_fetcher.cc b/common/http_fetcher.cc
new file mode 100644
index 0000000..400b43c
--- /dev/null
+++ b/common/http_fetcher.cc
@@ -0,0 +1,82 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/http_fetcher.h"
+
+#include <base/bind.h>
+
+using base::Closure;
+using brillo::MessageLoop;
+using std::deque;
+using std::string;
+
+namespace chromeos_update_engine {
+
+HttpFetcher::~HttpFetcher() {
+  if (no_resolver_idle_id_ != MessageLoop::kTaskIdNull) {
+    MessageLoop::current()->CancelTask(no_resolver_idle_id_);
+    no_resolver_idle_id_ = MessageLoop::kTaskIdNull;
+  }
+}
+
+void HttpFetcher::SetPostData(const void* data, size_t size,
+                              HttpContentType type) {
+  post_data_set_ = true;
+  post_data_.clear();
+  const char* char_data = reinterpret_cast<const char*>(data);
+  post_data_.insert(post_data_.end(), char_data, char_data + size);
+  post_content_type_ = type;
+}
+
+void HttpFetcher::SetPostData(const void* data, size_t size) {
+  SetPostData(data, size, kHttpContentTypeUnspecified);
+}
+
+// Proxy methods to set the proxies, then to pop them off.
+bool HttpFetcher::ResolveProxiesForUrl(const string& url,
+                                       const Closure& callback) {
+  CHECK_EQ(static_cast<Closure*>(nullptr), callback_.get());
+  callback_.reset(new Closure(callback));
+
+  if (!proxy_resolver_) {
+    LOG(INFO) << "Not resolving proxies (no proxy resolver).";
+    no_resolver_idle_id_ = MessageLoop::current()->PostTask(
+        FROM_HERE,
+        base::Bind(&HttpFetcher::NoProxyResolverCallback,
+                   base::Unretained(this)));
+    return true;
+  }
+  return proxy_resolver_->GetProxiesForUrl(url,
+                                           &HttpFetcher::StaticProxiesResolved,
+                                           this);
+}
+
+void HttpFetcher::NoProxyResolverCallback() {
+  ProxiesResolved(deque<string>());
+}
+
+void HttpFetcher::ProxiesResolved(const deque<string>& proxies) {
+  no_resolver_idle_id_ = MessageLoop::kTaskIdNull;
+  if (!proxies.empty())
+    SetProxies(proxies);
+  CHECK_NE(static_cast<Closure*>(nullptr), callback_.get());
+  Closure* callback = callback_.release();
+  // This may indirectly call back into ResolveProxiesForUrl():
+  callback->Run();
+  delete callback;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/http_fetcher.h b/common/http_fetcher.h
new file mode 100644
index 0000000..11e8e9f
--- /dev/null
+++ b/common/http_fetcher.h
@@ -0,0 +1,197 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_HTTP_FETCHER_H_
+#define UPDATE_ENGINE_COMMON_HTTP_FETCHER_H_
+
+#include <deque>
+#include <string>
+#include <vector>
+
+#include <base/callback.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/http_common.h"
+#include "update_engine/proxy_resolver.h"
+
+// This class is a simple wrapper around an HTTP library (libcurl). We can
+// easily mock out this interface for testing.
+
+// Implementations of this class should use asynchronous i/o. They can access
+// the MessageLoop to request callbacks when timers or file descriptors change.
+
+namespace chromeos_update_engine {
+
+class HttpFetcherDelegate;
+
+class HttpFetcher {
+ public:
+  // |proxy_resolver| is the resolver that will be consulted for proxy
+  // settings. It may be null, in which case direct connections will
+  // be used. Does not take ownership of the resolver.
+  HttpFetcher(ProxyResolver* proxy_resolver)
+      : post_data_set_(false),
+        http_response_code_(0),
+        delegate_(nullptr),
+        proxies_(1, kNoProxy),
+        proxy_resolver_(proxy_resolver),
+        callback_(nullptr) {}
+  virtual ~HttpFetcher();
+
+  void set_delegate(HttpFetcherDelegate* delegate) { delegate_ = delegate; }
+  HttpFetcherDelegate* delegate() const { return delegate_; }
+  int http_response_code() const { return http_response_code_; }
+
+  // Optional: Post data to the server. The HttpFetcher should make a copy
+  // of this data and upload it via HTTP POST during the transfer. The type of
+  // the data is necessary for properly setting the Content-Type HTTP header.
+  void SetPostData(const void* data, size_t size, HttpContentType type);
+
+  // Same without a specified Content-Type.
+  void SetPostData(const void* data, size_t size);
+
+  // Proxy methods to set the proxies, then to pop them off.
+  // Returns true on success.
+  bool ResolveProxiesForUrl(const std::string& url,
+                            const base::Closure& callback);
+
+  void SetProxies(const std::deque<std::string>& proxies) {
+    proxies_ = proxies;
+  }
+  const std::string& GetCurrentProxy() const {
+    return proxies_.front();
+  }
+  bool HasProxy() const { return !proxies_.empty(); }
+  void PopProxy() { proxies_.pop_front(); }
+
+  // Downloading should resume from this offset
+  virtual void SetOffset(off_t offset) = 0;
+
+  // Set/unset the length of the range to be downloaded.
+  virtual void SetLength(size_t length) = 0;
+  virtual void UnsetLength() = 0;
+
+  // Begins the transfer to the specified URL. This fetcher instance should not
+  // be destroyed until either TransferComplete, or TransferTerminated is
+  // called.
+  virtual void BeginTransfer(const std::string& url) = 0;
+
+  // Aborts the transfer. The transfer may not abort right away -- delegate's
+  // TransferTerminated() will be called when the transfer is actually done.
+  virtual void TerminateTransfer() = 0;
+
+  // If data is coming in too quickly, you can call Pause() to pause the
+  // transfer. The delegate will not have ReceivedBytes() called while
+  // an HttpFetcher is paused.
+  virtual void Pause() = 0;
+
+  // Used to unpause an HttpFetcher and let the bytes stream in again.
+  // If a delegate is set, ReceivedBytes() may be called on it before
+  // Unpause() returns
+  virtual void Unpause() = 0;
+
+  // These two function are overloaded in LibcurlHttp fetcher to speed
+  // testing.
+  virtual void set_idle_seconds(int seconds) {}
+  virtual void set_retry_seconds(int seconds) {}
+
+  // Sets the values used to time out the connection if the transfer
+  // rate is less than |low_speed_bps| bytes/sec for more than
+  // |low_speed_sec| seconds.
+  virtual void set_low_speed_limit(int low_speed_bps, int low_speed_sec) = 0;
+
+  // Sets the connect timeout, e.g. the maximum amount of time willing
+  // to wait for establishing a connection to the server.
+  virtual void set_connect_timeout(int connect_timeout_seconds) = 0;
+
+  // Sets the number of allowed retries.
+  virtual void set_max_retry_count(int max_retry_count) = 0;
+
+  // Get the total number of bytes downloaded by fetcher.
+  virtual size_t GetBytesDownloaded() = 0;
+
+  ProxyResolver* proxy_resolver() const { return proxy_resolver_; }
+
+ protected:
+  // The URL we're actively fetching from
+  std::string url_;
+
+  // POST data for the transfer, and whether or not it was ever set
+  bool post_data_set_;
+  brillo::Blob post_data_;
+  HttpContentType post_content_type_;
+
+  // The server's HTTP response code from the last transfer. This
+  // field should be set to 0 when a new transfer is initiated, and
+  // set to the response code when the transfer is complete.
+  int http_response_code_;
+
+  // The delegate; may be null.
+  HttpFetcherDelegate* delegate_;
+
+  // Proxy servers
+  std::deque<std::string> proxies_;
+
+  ProxyResolver* const proxy_resolver_;
+
+  // The ID of the idle callback, used when we have no proxy resolver.
+  brillo::MessageLoop::TaskId no_resolver_idle_id_{
+      brillo::MessageLoop::kTaskIdNull};
+
+  // Callback for when we are resolving proxies
+  std::unique_ptr<base::Closure> callback_;
+
+ private:
+  // Callback from the proxy resolver
+  void ProxiesResolved(const std::deque<std::string>& proxies);
+  static void StaticProxiesResolved(const std::deque<std::string>& proxies,
+                                    void* data) {
+    reinterpret_cast<HttpFetcher*>(data)->ProxiesResolved(proxies);
+  }
+
+  // Callback used to run the proxy resolver callback when there is no
+  // |proxy_resolver_|.
+  void NoProxyResolverCallback();
+
+  DISALLOW_COPY_AND_ASSIGN(HttpFetcher);
+};
+
+// Interface for delegates
+class HttpFetcherDelegate {
+ public:
+  virtual ~HttpFetcherDelegate() = default;
+
+  // Called every time bytes are received.
+  virtual void ReceivedBytes(HttpFetcher* fetcher,
+                             const void* bytes,
+                             size_t length) = 0;
+
+  // Called if the fetcher seeks to a particular offset.
+  virtual void SeekToOffset(off_t offset) {}
+
+  // When a transfer has completed, exactly one of these two methods will be
+  // called. TransferTerminated is called when the transfer has been aborted
+  // through TerminateTransfer. TransferComplete is called in all other
+  // situations. It's OK to destroy the |fetcher| object in this callback.
+  virtual void TransferComplete(HttpFetcher* fetcher, bool successful) = 0;
+  virtual void TransferTerminated(HttpFetcher* fetcher) {}
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HTTP_FETCHER_H_
diff --git a/common/http_fetcher_unittest.cc b/common/http_fetcher_unittest.cc
new file mode 100644
index 0000000..17e360e
--- /dev/null
+++ b/common/http_fetcher_unittest.cc
@@ -0,0 +1,1138 @@
+//
+// Copyright (C) 2012 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 <netinet/in.h>
+#include <netinet/ip.h>
+#include <sys/socket.h>
+#include <unistd.h>
+
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/message_loop/message_loop.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/base_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <brillo/process.h>
+#include <brillo/streams/file_stream.h>
+#include <brillo/streams/stream.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/http_common.h"
+#include "update_engine/common/libcurl_http_fetcher.h"
+#include "update_engine/common/mock_http_fetcher.h"
+#include "update_engine/common/multi_range_http_fetcher.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/proxy_resolver.h"
+
+using brillo::MessageLoop;
+using std::make_pair;
+using std::pair;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace {
+
+const int kBigLength           = 100000;
+const int kMediumLength        = 1000;
+const int kFlakyTruncateLength = 29000;
+const int kFlakySleepEvery     = 3;
+const int kFlakySleepSecs      = 10;
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+static const char *kUnusedUrl = "unused://unused";
+
+static inline string LocalServerUrlForPath(in_port_t port,
+                                           const string& path) {
+  string port_str = (port ? base::StringPrintf(":%hu", port) : "");
+  return base::StringPrintf("http://127.0.0.1%s%s", port_str.c_str(),
+                            path.c_str());
+}
+
+//
+// Class hierarchy for HTTP server implementations.
+//
+
+class HttpServer {
+ public:
+  // This makes it an abstract class (dirty but works).
+  virtual ~HttpServer() = 0;
+
+  virtual in_port_t GetPort() const {
+    return 0;
+  }
+
+  bool started_;
+};
+
+HttpServer::~HttpServer() {}
+
+
+class NullHttpServer : public HttpServer {
+ public:
+  NullHttpServer() {
+    started_ = true;
+  }
+};
+
+
+class PythonHttpServer : public HttpServer {
+ public:
+  PythonHttpServer() : port_(0) {
+    started_ = false;
+
+    // Spawn the server process.
+    unique_ptr<brillo::Process> http_server(new brillo::ProcessImpl());
+    base::FilePath test_server_path =
+        test_utils::GetBuildArtifactsPath().Append("test_http_server");
+    http_server->AddArg(test_server_path.value());
+    http_server->RedirectUsingPipe(STDOUT_FILENO, false);
+
+    if (!http_server->Start()) {
+      ADD_FAILURE() << "failed to spawn http server process";
+      return;
+    }
+    LOG(INFO) << "started http server with pid " << http_server->pid();
+
+    // Wait for server to begin accepting connections, obtain its port.
+    brillo::StreamPtr stdout = brillo::FileStream::FromFileDescriptor(
+        http_server->GetPipe(STDOUT_FILENO), false /* own */, nullptr);
+    if (!stdout)
+      return;
+
+    vector<char> buf(128);
+    string line;
+    while (line.find('\n') == string::npos) {
+      size_t read;
+      if (!stdout->ReadBlocking(buf.data(), buf.size(), &read, nullptr)) {
+        ADD_FAILURE() << "error reading http server stdout";
+        return;
+      }
+      line.append(buf.data(), read);
+      if (read == 0)
+        break;
+    }
+    // Parse the port from the output line.
+    const size_t listening_msg_prefix_len = strlen(kServerListeningMsgPrefix);
+    if (line.size() < listening_msg_prefix_len) {
+      ADD_FAILURE() << "server output too short";
+      return;
+    }
+
+    EXPECT_EQ(kServerListeningMsgPrefix,
+              line.substr(0, listening_msg_prefix_len));
+    string port_str = line.substr(listening_msg_prefix_len);
+    port_str.resize(port_str.find('\n'));
+    EXPECT_TRUE(base::StringToUint(port_str, &port_));
+
+    started_ = true;
+    LOG(INFO) << "server running, listening on port " << port_;
+
+    // Any failure before this point will SIGKILL the test server if started
+    // when the |http_server| goes out of scope.
+    http_server_ = std::move(http_server);
+  }
+
+  ~PythonHttpServer() {
+    // If there's no process, do nothing.
+    if (!http_server_)
+      return;
+    // Wait up to 10 seconds for the process to finish. Destroying the process
+    // will kill it with a SIGKILL otherwise.
+    http_server_->Kill(SIGTERM, 10);
+  }
+
+  in_port_t GetPort() const override {
+    return port_;
+  }
+
+ private:
+  static const char* kServerListeningMsgPrefix;
+
+  unique_ptr<brillo::Process> http_server_;
+  unsigned int port_;
+};
+
+const char* PythonHttpServer::kServerListeningMsgPrefix = "listening on port ";
+
+//
+// Class hierarchy for HTTP fetcher test wrappers.
+//
+
+class AnyHttpFetcherTest {
+ public:
+  AnyHttpFetcherTest() {}
+  virtual ~AnyHttpFetcherTest() {}
+
+  virtual HttpFetcher* NewLargeFetcher(size_t num_proxies) = 0;
+  HttpFetcher* NewLargeFetcher() {
+    return NewLargeFetcher(1);
+  }
+
+  virtual HttpFetcher* NewSmallFetcher(size_t num_proxies) = 0;
+  HttpFetcher* NewSmallFetcher() {
+    return NewSmallFetcher(1);
+  }
+
+  virtual string BigUrl(in_port_t port) const { return kUnusedUrl; }
+  virtual string SmallUrl(in_port_t port) const { return kUnusedUrl; }
+  virtual string ErrorUrl(in_port_t port) const { return kUnusedUrl; }
+
+  virtual bool IsMock() const = 0;
+  virtual bool IsMulti() const = 0;
+
+  virtual void IgnoreServerAborting(HttpServer* server) const {}
+
+  virtual HttpServer* CreateServer() = 0;
+
+  FakeHardware* fake_hardware() {
+    return &fake_hardware_;
+  }
+
+ protected:
+  DirectProxyResolver proxy_resolver_;
+  FakeHardware fake_hardware_;
+};
+
+class MockHttpFetcherTest : public AnyHttpFetcherTest {
+ public:
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewLargeFetcher;
+  HttpFetcher* NewLargeFetcher(size_t num_proxies) override {
+    brillo::Blob big_data(1000000);
+    CHECK_GT(num_proxies, 0u);
+    proxy_resolver_.set_num_proxies(num_proxies);
+    return new MockHttpFetcher(
+        big_data.data(),
+        big_data.size(),
+        reinterpret_cast<ProxyResolver*>(&proxy_resolver_));
+  }
+
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewSmallFetcher;
+  HttpFetcher* NewSmallFetcher(size_t num_proxies) override {
+    CHECK_GT(num_proxies, 0u);
+    proxy_resolver_.set_num_proxies(num_proxies);
+    return new MockHttpFetcher(
+        "x",
+        1,
+        reinterpret_cast<ProxyResolver*>(&proxy_resolver_));
+  }
+
+  bool IsMock() const override { return true; }
+  bool IsMulti() const override { return false; }
+
+  HttpServer* CreateServer() override {
+    return new NullHttpServer;
+  }
+};
+
+class LibcurlHttpFetcherTest : public AnyHttpFetcherTest {
+ public:
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewLargeFetcher;
+  HttpFetcher* NewLargeFetcher(size_t num_proxies) override {
+    CHECK_GT(num_proxies, 0u);
+    proxy_resolver_.set_num_proxies(num_proxies);
+    LibcurlHttpFetcher *ret = new
+        LibcurlHttpFetcher(reinterpret_cast<ProxyResolver*>(&proxy_resolver_),
+                           &fake_hardware_);
+    // Speed up test execution.
+    ret->set_idle_seconds(1);
+    ret->set_retry_seconds(1);
+    fake_hardware_.SetIsOfficialBuild(false);
+    return ret;
+  }
+
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewSmallFetcher;
+  HttpFetcher* NewSmallFetcher(size_t num_proxies) override {
+    return NewLargeFetcher(num_proxies);
+  }
+
+  string BigUrl(in_port_t port) const override {
+    return LocalServerUrlForPath(port,
+                                 base::StringPrintf("/download/%d",
+                                                    kBigLength));
+  }
+  string SmallUrl(in_port_t port) const override {
+    return LocalServerUrlForPath(port, "/foo");
+  }
+  string ErrorUrl(in_port_t port) const override {
+    return LocalServerUrlForPath(port, "/error");
+  }
+
+  bool IsMock() const override { return false; }
+  bool IsMulti() const override { return false; }
+
+  void IgnoreServerAborting(HttpServer* server) const override {
+    // Nothing to do.
+  }
+
+  HttpServer* CreateServer() override {
+    return new PythonHttpServer;
+  }
+};
+
+class MultiRangeHttpFetcherTest : public LibcurlHttpFetcherTest {
+ public:
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewLargeFetcher;
+  HttpFetcher* NewLargeFetcher(size_t num_proxies) override {
+    CHECK_GT(num_proxies, 0u);
+    proxy_resolver_.set_num_proxies(num_proxies);
+    ProxyResolver* resolver =
+        reinterpret_cast<ProxyResolver*>(&proxy_resolver_);
+    MultiRangeHttpFetcher *ret =
+        new MultiRangeHttpFetcher(
+            new LibcurlHttpFetcher(resolver, &fake_hardware_));
+    ret->ClearRanges();
+    ret->AddRange(0);
+    // Speed up test execution.
+    ret->set_idle_seconds(1);
+    ret->set_retry_seconds(1);
+    fake_hardware_.SetIsOfficialBuild(false);
+    return ret;
+  }
+
+  // Necessary to unhide the definition in the base class.
+  using AnyHttpFetcherTest::NewSmallFetcher;
+  HttpFetcher* NewSmallFetcher(size_t num_proxies) override {
+    return NewLargeFetcher(num_proxies);
+  }
+
+  bool IsMulti() const override { return true; }
+};
+
+
+//
+// Infrastructure for type tests of HTTP fetcher.
+// See: http://code.google.com/p/googletest/wiki/AdvancedGuide#Typed_Tests
+//
+
+// Fixture class template. We use an explicit constraint to guarantee that it
+// can only be instantiated with an AnyHttpFetcherTest type, see:
+// http://www2.research.att.com/~bs/bs_faq2.html#constraints
+template <typename T>
+class HttpFetcherTest : public ::testing::Test {
+ public:
+  base::MessageLoopForIO base_loop_;
+  brillo::BaseMessageLoop loop_{&base_loop_};
+
+  T test_;
+
+ protected:
+  HttpFetcherTest() {
+    loop_.SetAsCurrent();
+  }
+
+  void TearDown() override {
+    EXPECT_EQ(0, brillo::MessageLoopRunMaxIterations(&loop_, 1));
+  }
+
+ private:
+  static void TypeConstraint(T* a) {
+    AnyHttpFetcherTest *b = a;
+    if (b == 0)  // Silence compiler warning of unused variable.
+      *b = a;
+  }
+};
+
+// Test case types list.
+typedef ::testing::Types<LibcurlHttpFetcherTest,
+                         MockHttpFetcherTest,
+                         MultiRangeHttpFetcherTest> HttpFetcherTestTypes;
+TYPED_TEST_CASE(HttpFetcherTest, HttpFetcherTestTypes);
+
+
+namespace {
+class HttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  HttpFetcherTestDelegate() :
+      is_expect_error_(false), times_transfer_complete_called_(0),
+      times_transfer_terminated_called_(0), times_received_bytes_called_(0) {}
+
+  void ReceivedBytes(HttpFetcher* /* fetcher */,
+                     const void* /* bytes */, size_t /* length */) override {
+    // Update counters
+    times_received_bytes_called_++;
+  }
+
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    if (is_expect_error_)
+      EXPECT_EQ(kHttpResponseNotFound, fetcher->http_response_code());
+    else
+      EXPECT_EQ(kHttpResponseOk, fetcher->http_response_code());
+    MessageLoop::current()->BreakLoop();
+
+    // Update counter
+    times_transfer_complete_called_++;
+  }
+
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+    times_transfer_terminated_called_++;
+  }
+
+  // Are we expecting an error response? (default: no)
+  bool is_expect_error_;
+
+  // Counters for callback invocations.
+  int times_transfer_complete_called_;
+  int times_transfer_terminated_called_;
+  int times_received_bytes_called_;
+};
+
+
+void StartTransfer(HttpFetcher* http_fetcher, const string& url) {
+  http_fetcher->BeginTransfer(url);
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, SimpleTest) {
+  HttpFetcherTestDelegate delegate;
+  unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+  fetcher->set_delegate(&delegate);
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  this->loop_.PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      this->test_.SmallUrl(server->GetPort())));
+  this->loop_.Run();
+}
+
+TYPED_TEST(HttpFetcherTest, SimpleBigTest) {
+  HttpFetcherTestDelegate delegate;
+  unique_ptr<HttpFetcher> fetcher(this->test_.NewLargeFetcher());
+  fetcher->set_delegate(&delegate);
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  this->loop_.PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      this->test_.BigUrl(server->GetPort())));
+  this->loop_.Run();
+}
+
+// Issue #9648: when server returns an error HTTP response, the fetcher needs to
+// terminate transfer prematurely, rather than try to process the error payload.
+TYPED_TEST(HttpFetcherTest, ErrorTest) {
+  if (this->test_.IsMock() || this->test_.IsMulti())
+    return;
+  HttpFetcherTestDelegate delegate;
+
+  // Delegate should expect an error response.
+  delegate.is_expect_error_ = true;
+
+  unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+  fetcher->set_delegate(&delegate);
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  this->loop_.PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      this->test_.ErrorUrl(server->GetPort())));
+  this->loop_.Run();
+
+  // Make sure that no bytes were received.
+  CHECK_EQ(delegate.times_received_bytes_called_, 0);
+  CHECK_EQ(fetcher->GetBytesDownloaded(), static_cast<size_t>(0));
+
+  // Make sure that transfer completion was signaled once, and no termination
+  // was signaled.
+  CHECK_EQ(delegate.times_transfer_complete_called_, 1);
+  CHECK_EQ(delegate.times_transfer_terminated_called_, 0);
+}
+
+namespace {
+class PausingHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* /* bytes */, size_t /* length */) override {
+    CHECK(!paused_);
+    paused_ = true;
+    fetcher->Pause();
+  }
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+  void Unpause() {
+    CHECK(paused_);
+    paused_ = false;
+    fetcher_->Unpause();
+  }
+  bool paused_;
+  HttpFetcher* fetcher_;
+};
+
+void UnpausingTimeoutCallback(PausingHttpFetcherTestDelegate* delegate,
+                              MessageLoop::TaskId* my_id) {
+  if (delegate->paused_)
+    delegate->Unpause();
+  // Update the task id with the new scheduled callback.
+  *my_id = MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&UnpausingTimeoutCallback, delegate, my_id),
+      base::TimeDelta::FromMilliseconds(200));
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, PauseTest) {
+  {
+    PausingHttpFetcherTestDelegate delegate;
+    unique_ptr<HttpFetcher> fetcher(this->test_.NewLargeFetcher());
+    delegate.paused_ = false;
+    delegate.fetcher_ = fetcher.get();
+    fetcher->set_delegate(&delegate);
+
+    unique_ptr<HttpServer> server(this->test_.CreateServer());
+    ASSERT_TRUE(server->started_);
+
+    MessageLoop::TaskId callback_id;
+    callback_id = this->loop_.PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&UnpausingTimeoutCallback, &delegate, &callback_id),
+        base::TimeDelta::FromMilliseconds(200));
+    fetcher->BeginTransfer(this->test_.BigUrl(server->GetPort()));
+
+    this->loop_.Run();
+    EXPECT_TRUE(this->loop_.CancelTask(callback_id));
+  }
+}
+
+namespace {
+class AbortingHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {}
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    ADD_FAILURE();  // We should never get here
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    EXPECT_EQ(fetcher, fetcher_.get());
+    EXPECT_FALSE(once_);
+    EXPECT_TRUE(callback_once_);
+    callback_once_ = false;
+    // The fetcher could have a callback scheduled on the ProxyResolver that
+    // can fire after this callback. We wait until the end of the test to
+    // delete the fetcher.
+  }
+  void TerminateTransfer() {
+    CHECK(once_);
+    once_ = false;
+    fetcher_->TerminateTransfer();
+  }
+  void EndLoop() {
+    MessageLoop::current()->BreakLoop();
+  }
+  bool once_;
+  bool callback_once_;
+  unique_ptr<HttpFetcher> fetcher_;
+};
+
+void AbortingTimeoutCallback(AbortingHttpFetcherTestDelegate* delegate,
+                             MessageLoop::TaskId* my_id) {
+  if (delegate->once_) {
+    delegate->TerminateTransfer();
+    *my_id = MessageLoop::current()->PostTask(
+        FROM_HERE,
+        base::Bind(AbortingTimeoutCallback, delegate, my_id));
+  } else {
+    delegate->EndLoop();
+    *my_id = MessageLoop::kTaskIdNull;
+  }
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, AbortTest) {
+  AbortingHttpFetcherTestDelegate delegate;
+  delegate.fetcher_.reset(this->test_.NewLargeFetcher());
+  delegate.once_ = true;
+  delegate.callback_once_ = true;
+  delegate.fetcher_->set_delegate(&delegate);
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  this->test_.IgnoreServerAborting(server.get());
+  ASSERT_TRUE(server->started_);
+
+  MessageLoop::TaskId task_id = MessageLoop::kTaskIdNull;
+
+  task_id = this->loop_.PostTask(
+      FROM_HERE,
+      base::Bind(AbortingTimeoutCallback, &delegate, &task_id));
+  delegate.fetcher_->BeginTransfer(this->test_.BigUrl(server->GetPort()));
+
+  this->loop_.Run();
+  CHECK(!delegate.once_);
+  CHECK(!delegate.callback_once_);
+  this->loop_.CancelTask(task_id);
+}
+
+namespace {
+class FlakyHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {
+    data.append(reinterpret_cast<const char*>(bytes), length);
+  }
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    EXPECT_TRUE(successful);
+    EXPECT_EQ(kHttpResponsePartialContent, fetcher->http_response_code());
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+  string data;
+};
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, FlakyTest) {
+  if (this->test_.IsMock())
+    return;
+  {
+    FlakyHttpFetcherTestDelegate delegate;
+    unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+    fetcher->set_delegate(&delegate);
+
+    unique_ptr<HttpServer> server(this->test_.CreateServer());
+    ASSERT_TRUE(server->started_);
+
+    this->loop_.PostTask(FROM_HERE, base::Bind(
+        &StartTransfer,
+        fetcher.get(),
+        LocalServerUrlForPath(server->GetPort(),
+                              base::StringPrintf("/flaky/%d/%d/%d/%d",
+                                                 kBigLength,
+                                                 kFlakyTruncateLength,
+                                                 kFlakySleepEvery,
+                                                 kFlakySleepSecs))));
+    this->loop_.Run();
+
+    // verify the data we get back
+    ASSERT_EQ(kBigLength, delegate.data.size());
+    for (int i = 0; i < kBigLength; i += 10) {
+      // Assert so that we don't flood the screen w/ EXPECT errors on failure.
+      ASSERT_EQ(delegate.data.substr(i, 10), "abcdefghij");
+    }
+  }
+}
+
+namespace {
+// This delegate kills the server attached to it after receiving any bytes.
+// This can be used for testing what happens when you try to fetch data and
+// the server dies.
+class FailureHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  explicit FailureHttpFetcherTestDelegate(PythonHttpServer* server)
+      : server_(server) {}
+
+  ~FailureHttpFetcherTestDelegate() override {
+    if (server_) {
+      LOG(INFO) << "Stopping server in destructor";
+      delete server_;
+      LOG(INFO) << "server stopped";
+    }
+  }
+
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {
+    if (server_) {
+      LOG(INFO) << "Stopping server in ReceivedBytes";
+      delete server_;
+      LOG(INFO) << "server stopped";
+      server_ = nullptr;
+    }
+  }
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    EXPECT_FALSE(successful);
+    EXPECT_EQ(0, fetcher->http_response_code());
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+  PythonHttpServer* server_;
+};
+}  // namespace
+
+
+TYPED_TEST(HttpFetcherTest, FailureTest) {
+  // This test ensures that a fetcher responds correctly when a server isn't
+  // available at all.
+  if (this->test_.IsMock())
+    return;
+  {
+    FailureHttpFetcherTestDelegate delegate(nullptr);
+    unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+    fetcher->set_delegate(&delegate);
+
+    this->loop_.PostTask(FROM_HERE,
+                         base::Bind(StartTransfer,
+                                    fetcher.get(),
+                                    "http://host_doesnt_exist99999999"));
+    this->loop_.Run();
+
+    // Exiting and testing happens in the delegate
+  }
+}
+
+TYPED_TEST(HttpFetcherTest, NoResponseTest) {
+  // This test starts a new http server but the server doesn't respond and just
+  // closes the connection.
+  if (this->test_.IsMock())
+    return;
+
+  PythonHttpServer* server = new PythonHttpServer();
+  int port = server->GetPort();
+  ASSERT_TRUE(server->started_);
+
+  // Handles destruction and claims ownership.
+  FailureHttpFetcherTestDelegate delegate(server);
+  unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+  fetcher->set_delegate(&delegate);
+  // The server will not reply at all, so we can limit the execution time of the
+  // test by reducing the low-speed timeout to something small. The test will
+  // finish once the TimeoutCallback() triggers (every second) and the timeout
+  // expired.
+  fetcher->set_low_speed_limit(kDownloadLowSpeedLimitBps, 1);
+
+  this->loop_.PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      LocalServerUrlForPath(port, "/hang")));
+  this->loop_.Run();
+
+  // Check that no other callback runs in the next two seconds. That would
+  // indicate a leaked callback.
+  bool timeout = false;
+  auto callback = base::Bind([&timeout]{ timeout = true;});
+  this->loop_.PostDelayedTask(FROM_HERE, callback,
+                              base::TimeDelta::FromSeconds(2));
+  EXPECT_TRUE(this->loop_.RunOnce(true));
+  EXPECT_TRUE(timeout);
+}
+
+TYPED_TEST(HttpFetcherTest, ServerDiesTest) {
+  // This test starts a new http server and kills it after receiving its first
+  // set of bytes. It test whether or not our fetcher eventually gives up on
+  // retries and aborts correctly.
+  if (this->test_.IsMock())
+    return;
+  {
+    PythonHttpServer* server = new PythonHttpServer();
+    int port = server->GetPort();
+    ASSERT_TRUE(server->started_);
+
+    // Handles destruction and claims ownership.
+    FailureHttpFetcherTestDelegate delegate(server);
+    unique_ptr<HttpFetcher> fetcher(this->test_.NewSmallFetcher());
+    fetcher->set_delegate(&delegate);
+
+    this->loop_.PostTask(FROM_HERE, base::Bind(
+        StartTransfer,
+        fetcher.get(),
+        LocalServerUrlForPath(port,
+                              base::StringPrintf("/flaky/%d/%d/%d/%d",
+                                                 kBigLength,
+                                                 kFlakyTruncateLength,
+                                                 kFlakySleepEvery,
+                                                 kFlakySleepSecs))));
+    this->loop_.Run();
+
+    // Exiting and testing happens in the delegate
+  }
+}
+
+namespace {
+const HttpResponseCode kRedirectCodes[] = {
+  kHttpResponseMovedPermanently, kHttpResponseFound, kHttpResponseSeeOther,
+  kHttpResponseTempRedirect
+};
+
+class RedirectHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  explicit RedirectHttpFetcherTestDelegate(bool expected_successful)
+      : expected_successful_(expected_successful) {}
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {
+    data.append(reinterpret_cast<const char*>(bytes), length);
+  }
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    EXPECT_EQ(expected_successful_, successful);
+    if (expected_successful_) {
+      EXPECT_EQ(kHttpResponseOk, fetcher->http_response_code());
+    } else {
+      EXPECT_GE(fetcher->http_response_code(), kHttpResponseMovedPermanently);
+      EXPECT_LE(fetcher->http_response_code(), kHttpResponseTempRedirect);
+    }
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+  bool expected_successful_;
+  string data;
+};
+
+// RedirectTest takes ownership of |http_fetcher|.
+void RedirectTest(const HttpServer* server,
+                  bool expected_successful,
+                  const string& url,
+                  HttpFetcher* http_fetcher) {
+  RedirectHttpFetcherTestDelegate delegate(expected_successful);
+  unique_ptr<HttpFetcher> fetcher(http_fetcher);
+  fetcher->set_delegate(&delegate);
+
+  MessageLoop::current()->PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      LocalServerUrlForPath(server->GetPort(), url)));
+  MessageLoop::current()->Run();
+  if (expected_successful) {
+    // verify the data we get back
+    ASSERT_EQ(kMediumLength, delegate.data.size());
+    for (int i = 0; i < kMediumLength; i += 10) {
+      // Assert so that we don't flood the screen w/ EXPECT errors on failure.
+      ASSERT_EQ(delegate.data.substr(i, 10), "abcdefghij");
+    }
+  }
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, SimpleRedirectTest) {
+  if (this->test_.IsMock())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  for (size_t c = 0; c < arraysize(kRedirectCodes); ++c) {
+    const string url = base::StringPrintf("/redirect/%d/download/%d",
+                                          kRedirectCodes[c],
+                                          kMediumLength);
+    RedirectTest(server.get(), true, url, this->test_.NewLargeFetcher());
+  }
+}
+
+TYPED_TEST(HttpFetcherTest, MaxRedirectTest) {
+  if (this->test_.IsMock())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  string url;
+  for (int r = 0; r < kDownloadMaxRedirects; r++) {
+    url += base::StringPrintf("/redirect/%d",
+                              kRedirectCodes[r % arraysize(kRedirectCodes)]);
+  }
+  url += base::StringPrintf("/download/%d", kMediumLength);
+  RedirectTest(server.get(), true, url, this->test_.NewLargeFetcher());
+}
+
+TYPED_TEST(HttpFetcherTest, BeyondMaxRedirectTest) {
+  if (this->test_.IsMock())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  string url;
+  for (int r = 0; r < kDownloadMaxRedirects + 1; r++) {
+    url += base::StringPrintf("/redirect/%d",
+                              kRedirectCodes[r % arraysize(kRedirectCodes)]);
+  }
+  url += base::StringPrintf("/download/%d", kMediumLength);
+  RedirectTest(server.get(), false, url, this->test_.NewLargeFetcher());
+}
+
+namespace {
+class MultiHttpFetcherTestDelegate : public HttpFetcherDelegate {
+ public:
+  explicit MultiHttpFetcherTestDelegate(int expected_response_code)
+      : expected_response_code_(expected_response_code) {}
+
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {
+    EXPECT_EQ(fetcher, fetcher_.get());
+    data.append(reinterpret_cast<const char*>(bytes), length);
+  }
+
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    EXPECT_EQ(fetcher, fetcher_.get());
+    EXPECT_EQ(expected_response_code_ != kHttpResponseUndefined, successful);
+    if (expected_response_code_ != 0)
+      EXPECT_EQ(expected_response_code_, fetcher->http_response_code());
+    // Destroy the fetcher (because we're allowed to).
+    fetcher_.reset(nullptr);
+    MessageLoop::current()->BreakLoop();
+  }
+
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+
+  unique_ptr<HttpFetcher> fetcher_;
+  int expected_response_code_;
+  string data;
+};
+
+void MultiTest(HttpFetcher* fetcher_in,
+               FakeHardware* fake_hardware,
+               const string& url,
+               const vector<pair<off_t, off_t>>& ranges,
+               const string& expected_prefix,
+               off_t expected_size,
+               HttpResponseCode expected_response_code) {
+  MultiHttpFetcherTestDelegate delegate(expected_response_code);
+  delegate.fetcher_.reset(fetcher_in);
+
+  MultiRangeHttpFetcher* multi_fetcher =
+      dynamic_cast<MultiRangeHttpFetcher*>(fetcher_in);
+  ASSERT_TRUE(multi_fetcher);
+  multi_fetcher->ClearRanges();
+  for (vector<pair<off_t, off_t>>::const_iterator it = ranges.begin(),
+           e = ranges.end(); it != e; ++it) {
+    string tmp_str = base::StringPrintf("%jd+", it->first);
+    if (it->second > 0) {
+      base::StringAppendF(&tmp_str, "%jd", it->second);
+      multi_fetcher->AddRange(it->first, it->second);
+    } else {
+      base::StringAppendF(&tmp_str, "?");
+      multi_fetcher->AddRange(it->first);
+    }
+    LOG(INFO) << "added range: " << tmp_str;
+  }
+  fake_hardware->SetIsOfficialBuild(false);
+  multi_fetcher->set_delegate(&delegate);
+
+  MessageLoop::current()->PostTask(
+      FROM_HERE,
+      base::Bind(StartTransfer, multi_fetcher, url));
+  MessageLoop::current()->Run();
+
+  EXPECT_EQ(expected_size, delegate.data.size());
+  EXPECT_EQ(expected_prefix,
+            string(delegate.data.data(), expected_prefix.size()));
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherSimpleTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(0, 25));
+  ranges.push_back(make_pair(99, 0));
+  MultiTest(this->test_.NewLargeFetcher(),
+            this->test_.fake_hardware(),
+            this->test_.BigUrl(server->GetPort()),
+            ranges,
+            "abcdefghijabcdefghijabcdejabcdefghijabcdef",
+            kBigLength - (99 - 25),
+            kHttpResponsePartialContent);
+}
+
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherLengthLimitTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(0, 24));
+  MultiTest(this->test_.NewLargeFetcher(),
+            this->test_.fake_hardware(),
+            this->test_.BigUrl(server->GetPort()),
+            ranges,
+            "abcdefghijabcdefghijabcd",
+            24,
+            kHttpResponsePartialContent);
+}
+
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherMultiEndTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(kBigLength - 2, 0));
+  ranges.push_back(make_pair(kBigLength - 3, 0));
+  MultiTest(this->test_.NewLargeFetcher(),
+            this->test_.fake_hardware(),
+            this->test_.BigUrl(server->GetPort()),
+            ranges,
+            "ijhij",
+            5,
+            kHttpResponsePartialContent);
+}
+
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherInsufficientTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(kBigLength - 2, 4));
+  for (int i = 0; i < 2; ++i) {
+    LOG(INFO) << "i = " << i;
+    MultiTest(this->test_.NewLargeFetcher(),
+              this->test_.fake_hardware(),
+              this->test_.BigUrl(server->GetPort()),
+              ranges,
+              "ij",
+              2,
+              kHttpResponseUndefined);
+    ranges.push_back(make_pair(0, 5));
+  }
+}
+
+// Issue #18143: when a fetch of a secondary chunk out of a chain, then it
+// should retry with other proxies listed before giving up.
+//
+// (1) successful recovery: The offset fetch will fail twice but succeed with
+// the third proxy.
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherErrorIfOffsetRecoverableTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(0, 25));
+  ranges.push_back(make_pair(99, 0));
+  MultiTest(this->test_.NewLargeFetcher(3),
+            this->test_.fake_hardware(),
+            LocalServerUrlForPath(server->GetPort(),
+                                  base::StringPrintf("/error-if-offset/%d/2",
+                                                     kBigLength)),
+            ranges,
+            "abcdefghijabcdefghijabcdejabcdefghijabcdef",
+            kBigLength - (99 - 25),
+            kHttpResponsePartialContent);
+}
+
+// (2) unsuccessful recovery: The offset fetch will fail repeatedly.  The
+// fetcher will signal a (failed) completed transfer to the delegate.
+TYPED_TEST(HttpFetcherTest, MultiHttpFetcherErrorIfOffsetUnrecoverableTest) {
+  if (!this->test_.IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(this->test_.CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  vector<pair<off_t, off_t>> ranges;
+  ranges.push_back(make_pair(0, 25));
+  ranges.push_back(make_pair(99, 0));
+  MultiTest(this->test_.NewLargeFetcher(2),
+            this->test_.fake_hardware(),
+            LocalServerUrlForPath(server->GetPort(),
+                                  base::StringPrintf("/error-if-offset/%d/3",
+                                                     kBigLength)),
+            ranges,
+            "abcdefghijabcdefghijabcde",  // only received the first chunk
+            25,
+            kHttpResponseUndefined);
+}
+
+
+
+namespace {
+class BlockedTransferTestDelegate : public HttpFetcherDelegate {
+ public:
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override {
+    ADD_FAILURE();
+  }
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override {
+    EXPECT_FALSE(successful);
+    MessageLoop::current()->BreakLoop();
+  }
+  void TransferTerminated(HttpFetcher* fetcher) override {
+    ADD_FAILURE();
+  }
+};
+
+void BlockedTransferTestHelper(AnyHttpFetcherTest* fetcher_test,
+                               bool is_official_build) {
+  if (fetcher_test->IsMock() || fetcher_test->IsMulti())
+    return;
+
+  unique_ptr<HttpServer> server(fetcher_test->CreateServer());
+  ASSERT_TRUE(server->started_);
+
+  BlockedTransferTestDelegate delegate;
+  unique_ptr<HttpFetcher> fetcher(fetcher_test->NewLargeFetcher());
+  LOG(INFO) << "is_official_build: " << is_official_build;
+  // NewLargeFetcher creates the HttpFetcher* with a FakeSystemState.
+  fetcher_test->fake_hardware()->SetIsOfficialBuild(is_official_build);
+  fetcher->set_delegate(&delegate);
+
+  MessageLoop::current()->PostTask(FROM_HERE, base::Bind(
+      StartTransfer,
+      fetcher.get(),
+      LocalServerUrlForPath(server->GetPort(),
+                            fetcher_test->SmallUrl(server->GetPort()))));
+  MessageLoop::current()->Run();
+}
+}  // namespace
+
+TYPED_TEST(HttpFetcherTest, BlockedTransferTest) {
+  BlockedTransferTestHelper(&this->test_, false);
+}
+
+TYPED_TEST(HttpFetcherTest, BlockedTransferOfficialBuildTest) {
+  BlockedTransferTestHelper(&this->test_, true);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/hwid_override.cc b/common/hwid_override.cc
new file mode 100644
index 0000000..8800e94
--- /dev/null
+++ b/common/hwid_override.cc
@@ -0,0 +1,46 @@
+//
+// Copyright (C) 2013 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 "update_engine/common/hwid_override.h"
+
+#include <map>
+#include <string>
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <brillo/key_value_store.h>
+
+using std::map;
+using std::string;
+
+namespace chromeos_update_engine {
+
+const char HwidOverride::kHwidOverrideKey[] = "HWID_OVERRIDE";
+
+HwidOverride::HwidOverride() {}
+
+HwidOverride::~HwidOverride() {}
+
+string HwidOverride::Read(const base::FilePath& root) {
+  brillo::KeyValueStore lsb_release;
+  lsb_release.Load(base::FilePath(root.value() + "/etc/lsb-release"));
+  string result;
+  if (lsb_release.GetString(kHwidOverrideKey, &result))
+    return result;
+  return "";
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/hwid_override.h b/common/hwid_override.h
new file mode 100644
index 0000000..d39b572
--- /dev/null
+++ b/common/hwid_override.h
@@ -0,0 +1,46 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_HWID_OVERRIDE_H_
+#define UPDATE_ENGINE_COMMON_HWID_OVERRIDE_H_
+
+#include <map>
+#include <string>
+
+#include <base/files/file_path.h>
+#include <base/macros.h>
+
+namespace chromeos_update_engine {
+
+// Class that allows HWID to be read from <root>/etc/lsb-release.
+class HwidOverride {
+ public:
+  HwidOverride();
+  ~HwidOverride();
+
+  // Read HWID from an /etc/lsb-release file under given root.
+  // An empty string is returned if there is any error.
+  static std::string Read(const base::FilePath& root);
+
+  static const char kHwidOverrideKey[];
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(HwidOverride);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_HWID_OVERRIDE_H_
diff --git a/common/hwid_override_unittest.cc b/common/hwid_override_unittest.cc
new file mode 100644
index 0000000..fff64bc
--- /dev/null
+++ b/common/hwid_override_unittest.cc
@@ -0,0 +1,67 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/hwid_override.h"
+
+#include <string>
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/files/scoped_temp_dir.h>
+#include <gtest/gtest.h>
+
+namespace chromeos_update_engine {
+
+class HwidOverrideTest : public ::testing::Test {
+ public:
+  HwidOverrideTest() {}
+  ~HwidOverrideTest() override = default;
+
+  void SetUp() override {
+    ASSERT_TRUE(tempdir_.CreateUniqueTempDir());
+    ASSERT_TRUE(base::CreateDirectory(tempdir_.path().Append("etc")));
+  }
+
+ protected:
+  base::ScopedTempDir tempdir_;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(HwidOverrideTest);
+};
+
+TEST_F(HwidOverrideTest, ReadGood) {
+  std::string expected_hwid("expected");
+  std::string keyval(HwidOverride::kHwidOverrideKey);
+  keyval += ("=" + expected_hwid);
+  ASSERT_EQ(base::WriteFile(tempdir_.path().Append("etc/lsb-release"),
+                            keyval.c_str(), keyval.length()),
+            keyval.length());
+  EXPECT_EQ(expected_hwid, HwidOverride::Read(tempdir_.path()));
+}
+
+TEST_F(HwidOverrideTest, ReadNothing) {
+  std::string keyval("SOMETHING_ELSE=UNINTERESTING");
+  ASSERT_EQ(base::WriteFile(tempdir_.path().Append("etc/lsb-release"),
+                            keyval.c_str(), keyval.length()),
+            keyval.length());
+  EXPECT_EQ(std::string(), HwidOverride::Read(tempdir_.path()));
+}
+
+TEST_F(HwidOverrideTest, ReadFailure) {
+  EXPECT_EQ(std::string(), HwidOverride::Read(tempdir_.path()));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/libcurl_http_fetcher.cc b/common/libcurl_http_fetcher.cc
new file mode 100644
index 0000000..13784fa
--- /dev/null
+++ b/common/libcurl_http_fetcher.cc
@@ -0,0 +1,587 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/libcurl_http_fetcher.h"
+
+#include <algorithm>
+#include <string>
+
+#include <base/bind.h>
+#include <base/format_macros.h>
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/platform_constants.h"
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using std::max;
+using std::string;
+
+// This is a concrete implementation of HttpFetcher that uses libcurl to do the
+// http work.
+
+namespace chromeos_update_engine {
+
+namespace {
+const int kNoNetworkRetrySeconds = 10;
+}  // namespace
+
+LibcurlHttpFetcher::LibcurlHttpFetcher(ProxyResolver* proxy_resolver,
+                                       HardwareInterface* hardware)
+    : HttpFetcher(proxy_resolver), hardware_(hardware) {
+  // Dev users want a longer timeout (180 seconds) because they may
+  // be waiting on the dev server to build an image.
+  if (!hardware_->IsOfficialBuild())
+    low_speed_time_seconds_ = kDownloadDevModeLowSpeedTimeSeconds;
+  if (!hardware_->IsOOBEComplete(nullptr))
+    max_retry_count_ = kDownloadMaxRetryCountOobeNotComplete;
+}
+
+LibcurlHttpFetcher::~LibcurlHttpFetcher() {
+  LOG_IF(ERROR, transfer_in_progress_)
+      << "Destroying the fetcher while a transfer is in progress.";
+  CleanUp();
+}
+
+bool LibcurlHttpFetcher::GetProxyType(const string& proxy,
+                                      curl_proxytype* out_type) {
+  if (base::StartsWithASCII(proxy, "socks5://", true) ||
+      base::StartsWithASCII(proxy, "socks://", true)) {
+    *out_type = CURLPROXY_SOCKS5_HOSTNAME;
+    return true;
+  }
+  if (base::StartsWithASCII(proxy, "socks4://", true)) {
+    *out_type = CURLPROXY_SOCKS4A;
+    return true;
+  }
+  if (base::StartsWithASCII(proxy, "http://", true) ||
+      base::StartsWithASCII(proxy, "https://", true)) {
+    *out_type = CURLPROXY_HTTP;
+    return true;
+  }
+  if (base::StartsWithASCII(proxy, kNoProxy, true)) {
+    // known failure case. don't log.
+    return false;
+  }
+  LOG(INFO) << "Unknown proxy type: " << proxy;
+  return false;
+}
+
+void LibcurlHttpFetcher::ResumeTransfer(const string& url) {
+  LOG(INFO) << "Starting/Resuming transfer";
+  CHECK(!transfer_in_progress_);
+  url_ = url;
+  curl_multi_handle_ = curl_multi_init();
+  CHECK(curl_multi_handle_);
+
+  curl_handle_ = curl_easy_init();
+  CHECK(curl_handle_);
+
+  CHECK(HasProxy());
+  bool is_direct = (GetCurrentProxy() == kNoProxy);
+  LOG(INFO) << "Using proxy: " << (is_direct ? "no" : "yes");
+  if (is_direct) {
+    CHECK_EQ(curl_easy_setopt(curl_handle_,
+                              CURLOPT_PROXY,
+                              ""), CURLE_OK);
+  } else {
+    CHECK_EQ(curl_easy_setopt(curl_handle_,
+                              CURLOPT_PROXY,
+                              GetCurrentProxy().c_str()), CURLE_OK);
+    // Curl seems to require us to set the protocol
+    curl_proxytype type;
+    if (GetProxyType(GetCurrentProxy(), &type)) {
+      CHECK_EQ(curl_easy_setopt(curl_handle_,
+                                CURLOPT_PROXYTYPE,
+                                type), CURLE_OK);
+    }
+  }
+
+  if (post_data_set_) {
+    CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_POST, 1), CURLE_OK);
+    CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_POSTFIELDS,
+                              post_data_.data()),
+             CURLE_OK);
+    CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_POSTFIELDSIZE,
+                              post_data_.size()),
+             CURLE_OK);
+
+    // Set the Content-Type HTTP header, if one was specifically set.
+    CHECK(!curl_http_headers_);
+    if (post_content_type_ != kHttpContentTypeUnspecified) {
+      const string content_type_attr =
+        base::StringPrintf("Content-Type: %s",
+                           GetHttpContentTypeString(post_content_type_));
+      curl_http_headers_ = curl_slist_append(nullptr,
+                                             content_type_attr.c_str());
+      CHECK(curl_http_headers_);
+      CHECK_EQ(
+          curl_easy_setopt(curl_handle_, CURLOPT_HTTPHEADER,
+                           curl_http_headers_),
+          CURLE_OK);
+    } else {
+      LOG(WARNING) << "no content type set, using libcurl default";
+    }
+  }
+
+  if (bytes_downloaded_ > 0 || download_length_) {
+    // Resume from where we left off.
+    resume_offset_ = bytes_downloaded_;
+    CHECK_GE(resume_offset_, 0);
+
+    // Compute end offset, if one is specified. As per HTTP specification, this
+    // is an inclusive boundary. Make sure it doesn't overflow.
+    size_t end_offset = 0;
+    if (download_length_) {
+      end_offset = static_cast<size_t>(resume_offset_) + download_length_ - 1;
+      CHECK_LE((size_t) resume_offset_, end_offset);
+    }
+
+    // Create a string representation of the desired range.
+    string range_str = base::StringPrintf(
+        "%" PRIu64 "-", static_cast<uint64_t>(resume_offset_));
+    if (end_offset)
+      range_str += std::to_string(end_offset);
+    CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_RANGE, range_str.c_str()),
+             CURLE_OK);
+  }
+
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_WRITEDATA, this), CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_WRITEFUNCTION,
+                            StaticLibcurlWrite), CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_URL, url_.c_str()),
+           CURLE_OK);
+
+  // If the connection drops under |low_speed_limit_bps_| (10
+  // bytes/sec by default) for |low_speed_time_seconds_| (90 seconds,
+  // 180 on non-official builds), reconnect.
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_LOW_SPEED_LIMIT,
+                            low_speed_limit_bps_),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_LOW_SPEED_TIME,
+                            low_speed_time_seconds_),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_CONNECTTIMEOUT,
+                            connect_timeout_seconds_),
+           CURLE_OK);
+
+  // By default, libcurl doesn't follow redirections. Allow up to
+  // |kDownloadMaxRedirects| redirections.
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_FOLLOWLOCATION, 1), CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_MAXREDIRS,
+                            kDownloadMaxRedirects),
+           CURLE_OK);
+
+  // Lock down the appropriate curl options for HTTP or HTTPS depending on
+  // the url.
+  if (hardware_->IsOfficialBuild()) {
+    if (base::StartsWithASCII(url_, "http://", false))
+      SetCurlOptionsForHttp();
+    else
+      SetCurlOptionsForHttps();
+  } else {
+    LOG(INFO) << "Not setting http(s) curl options because we are "
+              << "running a dev/test image";
+  }
+
+  CHECK_EQ(curl_multi_add_handle(curl_multi_handle_, curl_handle_), CURLM_OK);
+  transfer_in_progress_ = true;
+}
+
+// Lock down only the protocol in case of HTTP.
+void LibcurlHttpFetcher::SetCurlOptionsForHttp() {
+  LOG(INFO) << "Setting up curl options for HTTP";
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_PROTOCOLS, CURLPROTO_HTTP),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_REDIR_PROTOCOLS,
+                            CURLPROTO_HTTP),
+           CURLE_OK);
+}
+
+// Security lock-down in official builds: makes sure that peer certificate
+// verification is enabled, restricts the set of trusted certificates,
+// restricts protocols to HTTPS, restricts ciphers to HIGH.
+void LibcurlHttpFetcher::SetCurlOptionsForHttps() {
+  LOG(INFO) << "Setting up curl options for HTTPS";
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_SSL_VERIFYPEER, 1),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_CAPATH,
+                            constants::kCACertificatesPath),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_PROTOCOLS, CURLPROTO_HTTPS),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_REDIR_PROTOCOLS,
+                            CURLPROTO_HTTPS),
+           CURLE_OK);
+  CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_SSL_CIPHER_LIST, "HIGH:!ADH"),
+           CURLE_OK);
+  if (server_to_check_ != ServerToCheck::kNone) {
+    CHECK_EQ(
+        curl_easy_setopt(curl_handle_, CURLOPT_SSL_CTX_DATA, &server_to_check_),
+        CURLE_OK);
+    CHECK_EQ(curl_easy_setopt(curl_handle_, CURLOPT_SSL_CTX_FUNCTION,
+                              CertificateChecker::ProcessSSLContext),
+             CURLE_OK);
+  }
+}
+
+
+// Begins the transfer, which must not have already been started.
+void LibcurlHttpFetcher::BeginTransfer(const string& url) {
+  CHECK(!transfer_in_progress_);
+  url_ = url;
+  auto closure = base::Bind(&LibcurlHttpFetcher::ProxiesResolved,
+                            base::Unretained(this));
+  if (!ResolveProxiesForUrl(url_, closure)) {
+    LOG(ERROR) << "Couldn't resolve proxies";
+    if (delegate_)
+      delegate_->TransferComplete(this, false);
+  }
+}
+
+void LibcurlHttpFetcher::ProxiesResolved() {
+  transfer_size_ = -1;
+  resume_offset_ = 0;
+  retry_count_ = 0;
+  no_network_retry_count_ = 0;
+  http_response_code_ = 0;
+  terminate_requested_ = false;
+  sent_byte_ = false;
+  ResumeTransfer(url_);
+  CurlPerformOnce();
+}
+
+void LibcurlHttpFetcher::ForceTransferTermination() {
+  CleanUp();
+  if (delegate_) {
+    // Note that after the callback returns this object may be destroyed.
+    delegate_->TransferTerminated(this);
+  }
+}
+
+void LibcurlHttpFetcher::TerminateTransfer() {
+  if (in_write_callback_) {
+    terminate_requested_ = true;
+  } else {
+    ForceTransferTermination();
+  }
+}
+
+void LibcurlHttpFetcher::CurlPerformOnce() {
+  CHECK(transfer_in_progress_);
+  int running_handles = 0;
+  CURLMcode retcode = CURLM_CALL_MULTI_PERFORM;
+
+  // libcurl may request that we immediately call curl_multi_perform after it
+  // returns, so we do. libcurl promises that curl_multi_perform will not block.
+  while (CURLM_CALL_MULTI_PERFORM == retcode) {
+    retcode = curl_multi_perform(curl_multi_handle_, &running_handles);
+    if (terminate_requested_) {
+      ForceTransferTermination();
+      return;
+    }
+  }
+  if (0 == running_handles) {
+    GetHttpResponseCode();
+    if (http_response_code_) {
+      LOG(INFO) << "HTTP response code: " << http_response_code_;
+      no_network_retry_count_ = 0;
+    } else {
+      LOG(ERROR) << "Unable to get http response code.";
+    }
+
+    // we're done!
+    CleanUp();
+
+    // TODO(petkov): This temporary code tries to deal with the case where the
+    // update engine performs an update check while the network is not ready
+    // (e.g., right after resume). Longer term, we should check if the network
+    // is online/offline and return an appropriate error code.
+    if (!sent_byte_ &&
+        http_response_code_ == 0 &&
+        no_network_retry_count_ < no_network_max_retries_) {
+      no_network_retry_count_++;
+      MessageLoop::current()->PostDelayedTask(
+          FROM_HERE,
+          base::Bind(&LibcurlHttpFetcher::RetryTimeoutCallback,
+                     base::Unretained(this)),
+          TimeDelta::FromSeconds(kNoNetworkRetrySeconds));
+      LOG(INFO) << "No HTTP response, retry " << no_network_retry_count_;
+      return;
+    }
+
+    if ((!sent_byte_ && !IsHttpResponseSuccess()) || IsHttpResponseError()) {
+      // The transfer completed w/ error and we didn't get any bytes.
+      // If we have another proxy to try, try that.
+      //
+      // TODO(garnold) in fact there are two separate cases here: one case is an
+      // other-than-success return code (including no return code) and no
+      // received bytes, which is necessary due to the way callbacks are
+      // currently processing error conditions;  the second is an explicit HTTP
+      // error code, where some data may have been received (as in the case of a
+      // semi-successful multi-chunk fetch).  This is a confusing behavior and
+      // should be unified into a complete, coherent interface.
+      LOG(INFO) << "Transfer resulted in an error (" << http_response_code_
+                << "), " << bytes_downloaded_ << " bytes downloaded";
+
+      PopProxy();  // Delete the proxy we just gave up on.
+
+      if (HasProxy()) {
+        // We have another proxy. Retry immediately.
+        LOG(INFO) << "Retrying with next proxy setting";
+        MessageLoop::current()->PostTask(
+            FROM_HERE,
+            base::Bind(&LibcurlHttpFetcher::RetryTimeoutCallback,
+                       base::Unretained(this)));
+      } else {
+        // Out of proxies. Give up.
+        LOG(INFO) << "No further proxies, indicating transfer complete";
+        if (delegate_)
+          delegate_->TransferComplete(this, false);  // signal fail
+      }
+    } else if ((transfer_size_ >= 0) && (bytes_downloaded_ < transfer_size_)) {
+      retry_count_++;
+      LOG(INFO) << "Transfer interrupted after downloading "
+                << bytes_downloaded_ << " of " << transfer_size_ << " bytes. "
+                << transfer_size_ - bytes_downloaded_ << " bytes remaining "
+                << "after " << retry_count_ << " attempt(s)";
+
+      if (retry_count_ > max_retry_count_) {
+        LOG(INFO) << "Reached max attempts (" << retry_count_ << ")";
+        if (delegate_)
+          delegate_->TransferComplete(this, false);  // signal fail
+      } else {
+        // Need to restart transfer
+        LOG(INFO) << "Restarting transfer to download the remaining bytes";
+        MessageLoop::current()->PostDelayedTask(
+            FROM_HERE,
+            base::Bind(&LibcurlHttpFetcher::RetryTimeoutCallback,
+                       base::Unretained(this)),
+            TimeDelta::FromSeconds(retry_seconds_));
+      }
+    } else {
+      LOG(INFO) << "Transfer completed (" << http_response_code_
+                << "), " << bytes_downloaded_ << " bytes downloaded";
+      if (delegate_) {
+        bool success = IsHttpResponseSuccess();
+        delegate_->TransferComplete(this, success);
+      }
+    }
+  } else {
+    // set up callback
+    SetupMessageLoopSources();
+  }
+}
+
+size_t LibcurlHttpFetcher::LibcurlWrite(void *ptr, size_t size, size_t nmemb) {
+  // Update HTTP response first.
+  GetHttpResponseCode();
+  const size_t payload_size = size * nmemb;
+
+  // Do nothing if no payload or HTTP response is an error.
+  if (payload_size == 0 || !IsHttpResponseSuccess()) {
+    LOG(INFO) << "HTTP response unsuccessful (" << http_response_code_
+              << ") or no payload (" << payload_size << "), nothing to do";
+    return 0;
+  }
+
+  sent_byte_ = true;
+  {
+    double transfer_size_double;
+    CHECK_EQ(curl_easy_getinfo(curl_handle_,
+                               CURLINFO_CONTENT_LENGTH_DOWNLOAD,
+                               &transfer_size_double), CURLE_OK);
+    off_t new_transfer_size = static_cast<off_t>(transfer_size_double);
+    if (new_transfer_size > 0) {
+      transfer_size_ = resume_offset_ + new_transfer_size;
+    }
+  }
+  bytes_downloaded_ += payload_size;
+  in_write_callback_ = true;
+  if (delegate_)
+    delegate_->ReceivedBytes(this, ptr, payload_size);
+  in_write_callback_ = false;
+  return payload_size;
+}
+
+void LibcurlHttpFetcher::Pause() {
+  CHECK(curl_handle_);
+  CHECK(transfer_in_progress_);
+  CHECK_EQ(curl_easy_pause(curl_handle_, CURLPAUSE_ALL), CURLE_OK);
+}
+
+void LibcurlHttpFetcher::Unpause() {
+  CHECK(curl_handle_);
+  CHECK(transfer_in_progress_);
+  CHECK_EQ(curl_easy_pause(curl_handle_, CURLPAUSE_CONT), CURLE_OK);
+}
+
+// This method sets up callbacks with the MessageLoop.
+void LibcurlHttpFetcher::SetupMessageLoopSources() {
+  fd_set fd_read;
+  fd_set fd_write;
+  fd_set fd_exc;
+
+  FD_ZERO(&fd_read);
+  FD_ZERO(&fd_write);
+  FD_ZERO(&fd_exc);
+
+  int fd_max = 0;
+
+  // Ask libcurl for the set of file descriptors we should track on its
+  // behalf.
+  CHECK_EQ(curl_multi_fdset(curl_multi_handle_, &fd_read, &fd_write,
+                            &fd_exc, &fd_max), CURLM_OK);
+
+  // We should iterate through all file descriptors up to libcurl's fd_max or
+  // the highest one we're tracking, whichever is larger.
+  for (size_t t = 0; t < arraysize(fd_task_maps_); ++t) {
+    if (!fd_task_maps_[t].empty())
+      fd_max = max(fd_max, fd_task_maps_[t].rbegin()->first);
+  }
+
+  // For each fd, if we're not tracking it, track it. If we are tracking it, but
+  // libcurl doesn't care about it anymore, stop tracking it. After this loop,
+  // there should be exactly as many tasks scheduled in fd_task_maps_[0|1] as
+  // there are read/write fds that we're tracking.
+  for (int fd = 0; fd <= fd_max; ++fd) {
+    // Note that fd_exc is unused in the current version of libcurl so is_exc
+    // should always be false.
+    bool is_exc = FD_ISSET(fd, &fd_exc) != 0;
+    bool must_track[2] = {
+      is_exc || (FD_ISSET(fd, &fd_read) != 0),  // track 0 -- read
+      is_exc || (FD_ISSET(fd, &fd_write) != 0)  // track 1 -- write
+    };
+    MessageLoop::WatchMode watch_modes[2] = {
+      MessageLoop::WatchMode::kWatchRead,
+      MessageLoop::WatchMode::kWatchWrite,
+    };
+
+    for (size_t t = 0; t < arraysize(fd_task_maps_); ++t) {
+      auto fd_task_it = fd_task_maps_[t].find(fd);
+      bool tracked = fd_task_it != fd_task_maps_[t].end();
+
+      if (!must_track[t]) {
+        // If we have an outstanding io_channel, remove it.
+        if (tracked) {
+          MessageLoop::current()->CancelTask(fd_task_it->second);
+          fd_task_maps_[t].erase(fd_task_it);
+        }
+        continue;
+      }
+
+      // If we are already tracking this fd, continue -- nothing to do.
+      if (tracked)
+        continue;
+
+      // Track a new fd.
+      fd_task_maps_[t][fd] = MessageLoop::current()->WatchFileDescriptor(
+          FROM_HERE,
+          fd,
+          watch_modes[t],
+          true,  // persistent
+          base::Bind(&LibcurlHttpFetcher::CurlPerformOnce,
+                     base::Unretained(this)));
+
+      static int io_counter = 0;
+      io_counter++;
+      if (io_counter % 50 == 0) {
+        LOG(INFO) << "io_counter = " << io_counter;
+      }
+    }
+  }
+
+  // Set up a timeout callback for libcurl.
+  if (timeout_id_ == MessageLoop::kTaskIdNull) {
+    LOG(INFO) << "Setting up timeout source: " << idle_seconds_ << " seconds.";
+    timeout_id_ = MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&LibcurlHttpFetcher::TimeoutCallback,
+                   base::Unretained(this)),
+        TimeDelta::FromSeconds(idle_seconds_));
+  }
+}
+
+void LibcurlHttpFetcher::RetryTimeoutCallback() {
+  ResumeTransfer(url_);
+  CurlPerformOnce();
+}
+
+void LibcurlHttpFetcher::TimeoutCallback() {
+  // We always re-schedule the callback, even if we don't want to be called
+  // anymore. We will remove the event source separately if we don't want to
+  // be called back.
+  timeout_id_ = MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&LibcurlHttpFetcher::TimeoutCallback, base::Unretained(this)),
+      TimeDelta::FromSeconds(idle_seconds_));
+
+  // CurlPerformOnce() may call CleanUp(), so we need to schedule our callback
+  // first, since it could be canceled by this call.
+  if (transfer_in_progress_)
+    CurlPerformOnce();
+}
+
+void LibcurlHttpFetcher::CleanUp() {
+  MessageLoop::current()->CancelTask(timeout_id_);
+  timeout_id_ = MessageLoop::kTaskIdNull;
+
+  for (size_t t = 0; t < arraysize(fd_task_maps_); ++t) {
+    for (const auto& fd_taks_pair : fd_task_maps_[t]) {
+      if (!MessageLoop::current()->CancelTask(fd_taks_pair.second)) {
+        LOG(WARNING) << "Error canceling the watch task "
+                     << fd_taks_pair.second << " for "
+                     << (t ? "writing" : "reading") << " the fd "
+                     << fd_taks_pair.first;
+      }
+    }
+    fd_task_maps_[t].clear();
+  }
+
+  if (curl_http_headers_) {
+    curl_slist_free_all(curl_http_headers_);
+    curl_http_headers_ = nullptr;
+  }
+  if (curl_handle_) {
+    if (curl_multi_handle_) {
+      CHECK_EQ(curl_multi_remove_handle(curl_multi_handle_, curl_handle_),
+               CURLM_OK);
+    }
+    curl_easy_cleanup(curl_handle_);
+    curl_handle_ = nullptr;
+  }
+  if (curl_multi_handle_) {
+    CHECK_EQ(curl_multi_cleanup(curl_multi_handle_), CURLM_OK);
+    curl_multi_handle_ = nullptr;
+  }
+  transfer_in_progress_ = false;
+}
+
+void LibcurlHttpFetcher::GetHttpResponseCode() {
+  long http_response_code = 0;  // NOLINT(runtime/int) - curl needs long.
+  if (curl_easy_getinfo(curl_handle_,
+                        CURLINFO_RESPONSE_CODE,
+                        &http_response_code) == CURLE_OK) {
+    http_response_code_ = static_cast<int>(http_response_code);
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/libcurl_http_fetcher.h b/common/libcurl_http_fetcher.h
new file mode 100644
index 0000000..900c973
--- /dev/null
+++ b/common/libcurl_http_fetcher.h
@@ -0,0 +1,249 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_LIBCURL_HTTP_FETCHER_H_
+#define UPDATE_ENGINE_COMMON_LIBCURL_HTTP_FETCHER_H_
+
+#include <map>
+#include <memory>
+#include <string>
+#include <utility>
+
+#include <curl/curl.h>
+
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/http_fetcher.h"
+
+// This is a concrete implementation of HttpFetcher that uses libcurl to do the
+// http work.
+
+namespace chromeos_update_engine {
+
+class LibcurlHttpFetcher : public HttpFetcher {
+ public:
+  LibcurlHttpFetcher(ProxyResolver* proxy_resolver,
+                     HardwareInterface* hardware);
+
+  // Cleans up all internal state. Does not notify delegate
+  ~LibcurlHttpFetcher() override;
+
+  void SetOffset(off_t offset) override { bytes_downloaded_ = offset; }
+
+  void SetLength(size_t length) override { download_length_ = length; }
+  void UnsetLength() override { SetLength(0); }
+
+  // Begins the transfer if it hasn't already begun.
+  void BeginTransfer(const std::string& url) override;
+
+  // If the transfer is in progress, aborts the transfer early. The transfer
+  // cannot be resumed.
+  void TerminateTransfer() override;
+
+  // Suspend the transfer by calling curl_easy_pause(CURLPAUSE_ALL).
+  void Pause() override;
+
+  // Resume the transfer by calling curl_easy_pause(CURLPAUSE_CONT).
+  void Unpause() override;
+
+  // Libcurl sometimes asks to be called back after some time while
+  // leaving that time unspecified. In that case, we pick a reasonable
+  // default of one second, but it can be overridden here. This is
+  // primarily useful for testing.
+  // From http://curl.haxx.se/libcurl/c/curl_multi_timeout.html:
+  //     if libcurl returns a -1 timeout here, it just means that libcurl
+  //     currently has no stored timeout value. You must not wait too long
+  //     (more than a few seconds perhaps) before you call
+  //     curl_multi_perform() again.
+  void set_idle_seconds(int seconds) override { idle_seconds_ = seconds; }
+
+  // Sets the retry timeout. Useful for testing.
+  void set_retry_seconds(int seconds) override { retry_seconds_ = seconds; }
+
+  void set_no_network_max_retries(int retries) {
+    no_network_max_retries_ = retries;
+  }
+
+  void set_server_to_check(ServerToCheck server_to_check) {
+    server_to_check_ = server_to_check;
+  }
+
+  size_t GetBytesDownloaded() override {
+    return static_cast<size_t>(bytes_downloaded_);
+  }
+
+  void set_low_speed_limit(int low_speed_bps, int low_speed_sec) override {
+    low_speed_limit_bps_ = low_speed_bps;
+    low_speed_time_seconds_ = low_speed_sec;
+  }
+
+  void set_connect_timeout(int connect_timeout_seconds) override {
+    connect_timeout_seconds_ = connect_timeout_seconds;
+  }
+
+  void set_max_retry_count(int max_retry_count) override {
+    max_retry_count_ = max_retry_count;
+  }
+
+ private:
+  // Callback for when proxy resolution has completed. This begins the
+  // transfer.
+  void ProxiesResolved();
+
+  // Asks libcurl for the http response code and stores it in the object.
+  void GetHttpResponseCode();
+
+  // Checks whether stored HTTP response is within the success range.
+  inline bool IsHttpResponseSuccess() {
+    return (http_response_code_ >= 200 && http_response_code_ < 300);
+  }
+
+  // Checks whether stored HTTP response is within the error range. This
+  // includes both errors with the request (4xx) and server errors (5xx).
+  inline bool IsHttpResponseError() {
+    return (http_response_code_ >= 400 && http_response_code_ < 600);
+  }
+
+  // Resumes a transfer where it left off. This will use the
+  // HTTP Range: header to make a new connection from where the last
+  // left off.
+  virtual void ResumeTransfer(const std::string& url);
+
+  void TimeoutCallback();
+  void RetryTimeoutCallback();
+
+  // Calls into curl_multi_perform to let libcurl do its work. Returns after
+  // curl_multi_perform is finished, which may actually be after more than
+  // one call to curl_multi_perform. This method will set up the message
+  // loop with sources for future work that libcurl will do.
+  // This method will not block.
+  // Returns true if we should resume immediately after this call.
+  void CurlPerformOnce();
+
+  // Sets up message loop sources as needed by libcurl. This is generally
+  // the file descriptor of the socket and a timer in case nothing happens
+  // on the fds.
+  void SetupMessageLoopSources();
+
+  // Callback called by libcurl when new data has arrived on the transfer
+  size_t LibcurlWrite(void *ptr, size_t size, size_t nmemb);
+  static size_t StaticLibcurlWrite(void *ptr, size_t size,
+                                   size_t nmemb, void *stream) {
+    return reinterpret_cast<LibcurlHttpFetcher*>(stream)->
+        LibcurlWrite(ptr, size, nmemb);
+  }
+
+  // Cleans up the following if they are non-null:
+  // curl(m) handles, fd_task_maps_, timeout_id_.
+  void CleanUp();
+
+  // Force terminate the transfer. This will invoke the delegate's (if any)
+  // TransferTerminated callback so, after returning, this fetcher instance may
+  // be destroyed.
+  void ForceTransferTermination();
+
+  // Sets the curl options for HTTP URL.
+  void SetCurlOptionsForHttp();
+
+  // Sets the curl options for HTTPS URL.
+  void SetCurlOptionsForHttps();
+
+  // Convert a proxy URL into a curl proxy type, if applicable. Returns true iff
+  // conversion was successful, false otherwise (in which case nothing is
+  // written to |out_type|).
+  bool GetProxyType(const std::string& proxy, curl_proxytype* out_type);
+
+  // Hardware interface used to query dev-mode and official build settings.
+  HardwareInterface* hardware_;
+
+  // Handles for the libcurl library
+  CURLM* curl_multi_handle_{nullptr};
+  CURL* curl_handle_{nullptr};
+  struct curl_slist* curl_http_headers_{nullptr};
+
+  // Lists of all read(0)/write(1) file descriptors that we're waiting on from
+  // the message loop. libcurl may open/close descriptors and switch their
+  // directions so maintain two separate lists so that watch conditions can be
+  // set appropriately.
+  std::map<int, brillo::MessageLoop::TaskId> fd_task_maps_[2];
+
+  // The TaskId of the timer we're waiting on. kTaskIdNull if we are not waiting
+  // on it.
+  brillo::MessageLoop::TaskId timeout_id_{brillo::MessageLoop::kTaskIdNull};
+
+  bool transfer_in_progress_{false};
+
+  // The transfer size. -1 if not known.
+  off_t transfer_size_{0};
+
+  // How many bytes have been downloaded and sent to the delegate.
+  off_t bytes_downloaded_{0};
+
+  // The remaining maximum number of bytes to download. Zero represents an
+  // unspecified length.
+  size_t download_length_{0};
+
+  // If we resumed an earlier transfer, data offset that we used for the
+  // new connection.  0 otherwise.
+  // In this class, resume refers to resuming a dropped HTTP connection,
+  // not to resuming an interrupted download.
+  off_t resume_offset_{0};
+
+  // Number of resumes performed so far and the max allowed.
+  int retry_count_{0};
+  int max_retry_count_{kDownloadMaxRetryCount};
+
+  // Seconds to wait before retrying a resume.
+  int retry_seconds_{20};
+
+  // Number of resumes due to no network (e.g., HTTP response code 0).
+  int no_network_retry_count_{0};
+  int no_network_max_retries_{0};
+
+  // Seconds to wait before asking libcurl to "perform".
+  int idle_seconds_{1};
+
+  // If true, we are currently performing a write callback on the delegate.
+  bool in_write_callback_{false};
+
+  // If true, we have returned at least one byte in the write callback
+  // to the delegate.
+  bool sent_byte_{false};
+
+  // We can't clean everything up while we're in a write callback, so
+  // if we get a terminate request, queue it until we can handle it.
+  bool terminate_requested_{false};
+
+  // The ServerToCheck used when checking this connection's certificate. If no
+  // certificate check needs to be performed, this should be set to
+  // ServerToCheck::kNone.
+  ServerToCheck server_to_check_{ServerToCheck::kNone};
+
+  int low_speed_limit_bps_{kDownloadLowSpeedLimitBps};
+  int low_speed_time_seconds_{kDownloadLowSpeedTimeSeconds};
+  int connect_timeout_seconds_{kDownloadConnectTimeoutSeconds};
+  int num_max_retries_;
+
+  DISALLOW_COPY_AND_ASSIGN(LibcurlHttpFetcher);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_LIBCURL_HTTP_FETCHER_H_
diff --git a/common/mock_certificate_checker.h b/common/mock_certificate_checker.h
new file mode 100644
index 0000000..1f55ca1
--- /dev/null
+++ b/common/mock_certificate_checker.h
@@ -0,0 +1,38 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_MOCK_CERTIFICATE_CHECKER_H_
+#define UPDATE_ENGINE_COMMON_MOCK_CERTIFICATE_CHECKER_H_
+
+#include <gmock/gmock.h>
+#include <openssl/ssl.h>
+
+#include "update_engine/common/certificate_checker.h"
+
+namespace chromeos_update_engine {
+
+class MockOpenSSLWrapper : public OpenSSLWrapper {
+ public:
+  MOCK_CONST_METHOD4(GetCertificateDigest,
+                     bool(X509_STORE_CTX* x509_ctx,
+                          int* out_depth,
+                          unsigned int* out_digest_length,
+                          uint8_t* out_digest));
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_MOCK_CERTIFICATE_CHECKER_H_
diff --git a/common/mock_hardware.h b/common/mock_hardware.h
new file mode 100644
index 0000000..451af91
--- /dev/null
+++ b/common/mock_hardware.h
@@ -0,0 +1,90 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_MOCK_HARDWARE_H_
+#define UPDATE_ENGINE_COMMON_MOCK_HARDWARE_H_
+
+#include <string>
+
+#include "update_engine/common/fake_hardware.h"
+
+#include <gmock/gmock.h>
+
+namespace chromeos_update_engine {
+
+// A mocked, fake implementation of HardwareInterface.
+class MockHardware : public HardwareInterface {
+ public:
+  MockHardware() {
+    // Delegate all calls to the fake instance
+    ON_CALL(*this, IsOfficialBuild())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::IsOfficialBuild));
+    ON_CALL(*this, IsNormalBootMode())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::IsNormalBootMode));
+    ON_CALL(*this, IsOOBEComplete(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::IsOOBEComplete));
+    ON_CALL(*this, GetHardwareClass())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetHardwareClass));
+    ON_CALL(*this, GetFirmwareVersion())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetFirmwareVersion));
+    ON_CALL(*this, GetECVersion())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetECVersion));
+    ON_CALL(*this, GetPowerwashCount())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetPowerwashCount));
+    ON_CALL(*this, GetNonVolatileDirectory(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetNonVolatileDirectory));
+    ON_CALL(*this, GetPowerwashSafeDirectory(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeHardware::GetPowerwashSafeDirectory));
+  }
+
+  ~MockHardware() override = default;
+
+  // Hardware overrides.
+  MOCK_CONST_METHOD0(IsOfficialBuild, bool());
+  MOCK_CONST_METHOD0(IsNormalBootMode, bool());
+  MOCK_CONST_METHOD1(IsOOBEComplete, bool(base::Time* out_time_of_oobe));
+  MOCK_CONST_METHOD0(GetHardwareClass, std::string());
+  MOCK_CONST_METHOD0(GetFirmwareVersion, std::string());
+  MOCK_CONST_METHOD0(GetECVersion, std::string());
+  MOCK_CONST_METHOD0(GetPowerwashCount, int());
+  MOCK_CONST_METHOD1(GetNonVolatileDirectory, bool(base::FilePath*));
+  MOCK_CONST_METHOD1(GetPowerwashSafeDirectory, bool(base::FilePath*));
+
+  // Returns a reference to the underlying FakeHardware.
+  FakeHardware& fake() {
+    return fake_;
+  }
+
+ private:
+  // The underlying FakeHardware.
+  FakeHardware fake_;
+
+  DISALLOW_COPY_AND_ASSIGN(MockHardware);
+};
+
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_MOCK_HARDWARE_H_
diff --git a/common/mock_http_fetcher.cc b/common/mock_http_fetcher.cc
new file mode 100644
index 0000000..f3fa70d
--- /dev/null
+++ b/common/mock_http_fetcher.cc
@@ -0,0 +1,149 @@
+//
+// Copyright (C) 2009 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 "update_engine/common/mock_http_fetcher.h"
+
+#include <algorithm>
+
+#include <base/bind.h>
+#include <base/logging.h>
+#include <base/time/time.h>
+#include <gtest/gtest.h>
+
+// This is a mock implementation of HttpFetcher which is useful for testing.
+
+using brillo::MessageLoop;
+using std::min;
+
+namespace chromeos_update_engine {
+
+MockHttpFetcher::~MockHttpFetcher() {
+  CHECK(timeout_id_ == MessageLoop::kTaskIdNull) <<
+      "Call TerminateTransfer() before dtor.";
+}
+
+void MockHttpFetcher::BeginTransfer(const std::string& url) {
+  EXPECT_FALSE(never_use_);
+  if (fail_transfer_ || data_.empty()) {
+    // No data to send, just notify of completion..
+    SignalTransferComplete();
+    return;
+  }
+  if (sent_size_ < data_.size())
+    SendData(true);
+}
+
+// Returns false on one condition: If timeout_id_ was already set
+// and it needs to be deleted by the caller. If timeout_id_ is null
+// when this function is called, this function will always return true.
+bool MockHttpFetcher::SendData(bool skip_delivery) {
+  if (fail_transfer_) {
+    SignalTransferComplete();
+    return timeout_id_ != MessageLoop::kTaskIdNull;
+  }
+
+  CHECK_LT(sent_size_, data_.size());
+  if (!skip_delivery) {
+    const size_t chunk_size = min(kMockHttpFetcherChunkSize,
+                                  data_.size() - sent_size_);
+    CHECK(delegate_);
+    delegate_->ReceivedBytes(this, &data_[sent_size_], chunk_size);
+    // We may get terminated in the callback.
+    if (sent_size_ == data_.size()) {
+      LOG(INFO) << "Terminated in the ReceivedBytes callback.";
+      return timeout_id_ != MessageLoop::kTaskIdNull;
+    }
+    sent_size_ += chunk_size;
+    CHECK_LE(sent_size_, data_.size());
+    if (sent_size_ == data_.size()) {
+      // We've sent all the data. Notify of success.
+      SignalTransferComplete();
+    }
+  }
+
+  if (paused_) {
+    // If we're paused, we should return true if timeout_id_ is set,
+    // since we need the caller to delete it.
+    return timeout_id_ != MessageLoop::kTaskIdNull;
+  }
+
+  if (timeout_id_ != MessageLoop::kTaskIdNull) {
+    // we still need a timeout if there's more data to send
+    return sent_size_ < data_.size();
+  } else if (sent_size_ < data_.size()) {
+    // we don't have a timeout source and we need one
+    timeout_id_ = MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&MockHttpFetcher::TimeoutCallback, base::Unretained(this)),
+        base::TimeDelta::FromMilliseconds(10));
+  }
+  return true;
+}
+
+void MockHttpFetcher::TimeoutCallback() {
+  CHECK(!paused_);
+  if (SendData(false)) {
+    // We need to re-schedule the timeout.
+    timeout_id_ = MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&MockHttpFetcher::TimeoutCallback, base::Unretained(this)),
+        base::TimeDelta::FromMilliseconds(10));
+  } else {
+    timeout_id_ = MessageLoop::kTaskIdNull;
+  }
+}
+
+// If the transfer is in progress, aborts the transfer early.
+// The transfer cannot be resumed.
+void MockHttpFetcher::TerminateTransfer() {
+  LOG(INFO) << "Terminating transfer.";
+  sent_size_ = data_.size();
+  // Kill any timeout, it is ok to call with kTaskIdNull.
+  MessageLoop::current()->CancelTask(timeout_id_);
+  timeout_id_ = MessageLoop::kTaskIdNull;
+  delegate_->TransferTerminated(this);
+}
+
+void MockHttpFetcher::Pause() {
+  CHECK(!paused_);
+  paused_ = true;
+  MessageLoop::current()->CancelTask(timeout_id_);
+  timeout_id_ = MessageLoop::kTaskIdNull;
+}
+
+void MockHttpFetcher::Unpause() {
+  CHECK(paused_) << "You must pause before unpause.";
+  paused_ = false;
+  if (sent_size_ < data_.size()) {
+    SendData(false);
+  }
+}
+
+void MockHttpFetcher::FailTransfer(int http_response_code) {
+  fail_transfer_ = true;
+  http_response_code_ = http_response_code;
+}
+
+void MockHttpFetcher::SignalTransferComplete() {
+  // If the transfer has been failed, the HTTP response code should be set
+  // already.
+  if (!fail_transfer_) {
+    http_response_code_ = 200;
+  }
+  delegate_->TransferComplete(this, !fail_transfer_);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/mock_http_fetcher.h b/common/mock_http_fetcher.h
new file mode 100644
index 0000000..90d34dd
--- /dev/null
+++ b/common/mock_http_fetcher.h
@@ -0,0 +1,146 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_MOCK_HTTP_FETCHER_H_
+#define UPDATE_ENGINE_COMMON_MOCK_HTTP_FETCHER_H_
+
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/http_fetcher.h"
+
+// This is a mock implementation of HttpFetcher which is useful for testing.
+// All data must be passed into the ctor. When started, MockHttpFetcher will
+// deliver the data in chunks of size kMockHttpFetcherChunkSize. To simulate
+// a network failure, you can call FailTransfer().
+
+namespace chromeos_update_engine {
+
+// MockHttpFetcher will send a chunk of data down in each call to BeginTransfer
+// and Unpause. For the other chunks of data, a callback is put on the run
+// loop and when that's called, another chunk is sent down.
+const size_t kMockHttpFetcherChunkSize(65536);
+
+class MockHttpFetcher : public HttpFetcher {
+ public:
+  // The data passed in here is copied and then passed to the delegate after
+  // the transfer begins.
+  MockHttpFetcher(const uint8_t* data,
+                  size_t size,
+                  ProxyResolver* proxy_resolver)
+      : HttpFetcher(proxy_resolver),
+        sent_size_(0),
+        timeout_id_(brillo::MessageLoop::kTaskIdNull),
+        paused_(false),
+        fail_transfer_(false),
+        never_use_(false) {
+    data_.insert(data_.end(), data, data + size);
+  }
+
+  // Constructor overload for string data.
+  MockHttpFetcher(const char* data, size_t size, ProxyResolver* proxy_resolver)
+      : MockHttpFetcher(reinterpret_cast<const uint8_t*>(data), size,
+                        proxy_resolver) {}
+
+  // Cleans up all internal state. Does not notify delegate
+  ~MockHttpFetcher() override;
+
+  // Ignores this.
+  void SetOffset(off_t offset) override {
+    sent_size_ = offset;
+    if (delegate_)
+      delegate_->SeekToOffset(offset);
+  }
+
+  // Do nothing.
+  void SetLength(size_t length) override {}
+  void UnsetLength() override {}
+  void set_low_speed_limit(int low_speed_bps, int low_speed_sec) override {}
+  void set_connect_timeout(int connect_timeout_seconds) override {}
+  void set_max_retry_count(int max_retry_count) override {}
+
+  // Dummy: no bytes were downloaded.
+  size_t GetBytesDownloaded() override {
+    return sent_size_;
+  }
+
+  // Begins the transfer if it hasn't already begun.
+  void BeginTransfer(const std::string& url) override;
+
+  // If the transfer is in progress, aborts the transfer early.
+  // The transfer cannot be resumed.
+  void TerminateTransfer() override;
+
+  // Suspend the mock transfer.
+  void Pause() override;
+
+  // Resume the mock transfer.
+  void Unpause() override;
+
+  // Fail the transfer. This simulates a network failure.
+  void FailTransfer(int http_response_code);
+
+  // If set to true, this will EXPECT fail on BeginTransfer
+  void set_never_use(bool never_use) { never_use_ = never_use; }
+
+  const brillo::Blob& post_data() const {
+    return post_data_;
+  }
+
+ private:
+  // Sends data to the delegate and sets up a timeout callback if needed.
+  // There must be a delegate and there must be data to send. If there is
+  // already a timeout callback, and it should be deleted by the caller,
+  // this will return false; otherwise true is returned.
+  // If skip_delivery is true, no bytes will be delivered, but the callbacks
+  // still be set if needed.
+  bool SendData(bool skip_delivery);
+
+  // Callback for when our message loop timeout expires.
+  void TimeoutCallback();
+
+  // Sets the HTTP response code and signals to the delegate that the transfer
+  // is complete.
+  void SignalTransferComplete();
+
+  // A full copy of the data we'll return to the delegate
+  brillo::Blob data_;
+
+  // The number of bytes we've sent so far
+  size_t sent_size_;
+
+  // The TaskId of the timeout callback. After each chunk of data sent, we
+  // time out for 0s just to make sure that run loop services other clients.
+  brillo::MessageLoop::TaskId timeout_id_;
+
+  // True iff the fetcher is paused.
+  bool paused_;
+
+  // Set to true if the transfer should fail.
+  bool fail_transfer_;
+
+  // Set to true if BeginTransfer should EXPECT fail.
+  bool never_use_;
+
+  DISALLOW_COPY_AND_ASSIGN(MockHttpFetcher);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_MOCK_HTTP_FETCHER_H_
diff --git a/common/mock_prefs.h b/common/mock_prefs.h
new file mode 100644
index 0000000..0e639a2
--- /dev/null
+++ b/common/mock_prefs.h
@@ -0,0 +1,51 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_MOCK_PREFS_H_
+#define UPDATE_ENGINE_COMMON_MOCK_PREFS_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/prefs_interface.h"
+
+namespace chromeos_update_engine {
+
+class MockPrefs : public PrefsInterface {
+ public:
+  MOCK_CONST_METHOD2(GetString,
+                     bool(const std::string& key, std::string* value));
+  MOCK_METHOD2(SetString, bool(const std::string& key,
+                               const std::string& value));
+  MOCK_CONST_METHOD2(GetInt64, bool(const std::string& key, int64_t* value));
+  MOCK_METHOD2(SetInt64, bool(const std::string& key, const int64_t value));
+
+  MOCK_CONST_METHOD2(GetBoolean, bool(const std::string& key, bool* value));
+  MOCK_METHOD2(SetBoolean, bool(const std::string& key, const bool value));
+
+  MOCK_CONST_METHOD1(Exists, bool(const std::string& key));
+  MOCK_METHOD1(Delete, bool(const std::string& key));
+
+  MOCK_METHOD2(AddObserver, void(const std::string& key, ObserverInterface*));
+  MOCK_METHOD2(RemoveObserver,
+               void(const std::string& key, ObserverInterface*));
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_MOCK_PREFS_H_
diff --git a/common/multi_range_http_fetcher.cc b/common/multi_range_http_fetcher.cc
new file mode 100644
index 0000000..0a97b6e
--- /dev/null
+++ b/common/multi_range_http_fetcher.cc
@@ -0,0 +1,190 @@
+//
+// Copyright (C) 2010 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 "update_engine/common/multi_range_http_fetcher.h"
+
+#include <base/strings/stringprintf.h>
+
+#include <algorithm>
+#include <string>
+
+#include "update_engine/common/utils.h"
+
+namespace chromeos_update_engine {
+
+// Begins the transfer to the specified URL.
+// State change: Stopped -> Downloading
+// (corner case: Stopped -> Stopped for an empty request)
+void MultiRangeHttpFetcher::BeginTransfer(const std::string& url) {
+  CHECK(!base_fetcher_active_) << "BeginTransfer but already active.";
+  CHECK(!pending_transfer_ended_) << "BeginTransfer but pending.";
+  CHECK(!terminating_) << "BeginTransfer but terminating.";
+
+  if (ranges_.empty()) {
+    // Note that after the callback returns this object may be destroyed.
+    if (delegate_)
+      delegate_->TransferComplete(this, true);
+    return;
+  }
+  url_ = url;
+  current_index_ = 0;
+  bytes_received_this_range_ = 0;
+  LOG(INFO) << "starting first transfer";
+  base_fetcher_->set_delegate(this);
+  StartTransfer();
+}
+
+// State change: Downloading -> Pending transfer ended
+void MultiRangeHttpFetcher::TerminateTransfer() {
+  if (!base_fetcher_active_) {
+    LOG(INFO) << "Called TerminateTransfer but not active.";
+    // Note that after the callback returns this object may be destroyed.
+    if (delegate_)
+      delegate_->TransferTerminated(this);
+    return;
+  }
+  terminating_ = true;
+
+  if (!pending_transfer_ended_) {
+    base_fetcher_->TerminateTransfer();
+  }
+}
+
+// State change: Stopped or Downloading -> Downloading
+void MultiRangeHttpFetcher::StartTransfer() {
+  if (current_index_ >= ranges_.size()) {
+    return;
+  }
+
+  Range range = ranges_[current_index_];
+  LOG(INFO) << "starting transfer of range " << range.ToString();
+
+  bytes_received_this_range_ = 0;
+  base_fetcher_->SetOffset(range.offset());
+  if (range.HasLength())
+    base_fetcher_->SetLength(range.length());
+  else
+    base_fetcher_->UnsetLength();
+  if (delegate_)
+    delegate_->SeekToOffset(range.offset());
+  base_fetcher_active_ = true;
+  base_fetcher_->BeginTransfer(url_);
+}
+
+// State change: Downloading -> Downloading or Pending transfer ended
+void MultiRangeHttpFetcher::ReceivedBytes(HttpFetcher* fetcher,
+                                          const void* bytes,
+                                          size_t length) {
+  CHECK_LT(current_index_, ranges_.size());
+  CHECK_EQ(fetcher, base_fetcher_.get());
+  CHECK(!pending_transfer_ended_);
+  size_t next_size = length;
+  Range range = ranges_[current_index_];
+  if (range.HasLength()) {
+    next_size = std::min(next_size,
+                         range.length() - bytes_received_this_range_);
+  }
+  LOG_IF(WARNING, next_size <= 0) << "Asked to write length <= 0";
+  if (delegate_) {
+    delegate_->ReceivedBytes(this, bytes, next_size);
+  }
+  bytes_received_this_range_ += length;
+  if (range.HasLength() && bytes_received_this_range_ >= range.length()) {
+    // Terminates the current fetcher. Waits for its TransferTerminated
+    // callback before starting the next range so that we don't end up
+    // signalling the delegate that the whole multi-transfer is complete
+    // before all fetchers are really done and cleaned up.
+    pending_transfer_ended_ = true;
+    LOG(INFO) << "terminating transfer";
+    fetcher->TerminateTransfer();
+  }
+}
+
+// State change: Downloading or Pending transfer ended -> Stopped
+void MultiRangeHttpFetcher::TransferEnded(HttpFetcher* fetcher,
+                                          bool successful) {
+  CHECK(base_fetcher_active_) << "Transfer ended unexpectedly.";
+  CHECK_EQ(fetcher, base_fetcher_.get());
+  pending_transfer_ended_ = false;
+  http_response_code_ = fetcher->http_response_code();
+  LOG(INFO) << "TransferEnded w/ code " << http_response_code_;
+  if (terminating_) {
+    LOG(INFO) << "Terminating.";
+    Reset();
+    // Note that after the callback returns this object may be destroyed.
+    if (delegate_)
+      delegate_->TransferTerminated(this);
+    return;
+  }
+
+  // If we didn't get enough bytes, it's failure
+  Range range = ranges_[current_index_];
+  if (range.HasLength()) {
+    if (bytes_received_this_range_ < range.length()) {
+      // Failure
+      LOG(INFO) << "Didn't get enough bytes. Ending w/ failure.";
+      Reset();
+      // Note that after the callback returns this object may be destroyed.
+      if (delegate_)
+        delegate_->TransferComplete(this, false);
+      return;
+    }
+    // We got enough bytes and there were bytes specified, so this is success.
+    successful = true;
+  }
+
+  // If we have another transfer, do that.
+  if (current_index_ + 1 < ranges_.size()) {
+    current_index_++;
+    LOG(INFO) << "Starting next transfer (" << current_index_ << ").";
+    StartTransfer();
+    return;
+  }
+
+  LOG(INFO) << "Done w/ all transfers";
+  Reset();
+  // Note that after the callback returns this object may be destroyed.
+  if (delegate_)
+    delegate_->TransferComplete(this, successful);
+}
+
+void MultiRangeHttpFetcher::TransferComplete(HttpFetcher* fetcher,
+                                             bool successful) {
+  LOG(INFO) << "Received transfer complete.";
+  TransferEnded(fetcher, successful);
+}
+
+void MultiRangeHttpFetcher::TransferTerminated(HttpFetcher* fetcher) {
+  LOG(INFO) << "Received transfer terminated.";
+  TransferEnded(fetcher, false);
+}
+
+void MultiRangeHttpFetcher::Reset() {
+  base_fetcher_active_ = pending_transfer_ended_ = terminating_ = false;
+  current_index_ = 0;
+  bytes_received_this_range_ = 0;
+}
+
+std::string MultiRangeHttpFetcher::Range::ToString() const {
+  std::string range_str = base::StringPrintf("%jd+", offset());
+  if (HasLength())
+    range_str += std::to_string(length());
+  else
+    range_str += "?";
+  return range_str;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/multi_range_http_fetcher.h b/common/multi_range_http_fetcher.h
new file mode 100644
index 0000000..8158a22
--- /dev/null
+++ b/common/multi_range_http_fetcher.h
@@ -0,0 +1,179 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_MULTI_RANGE_HTTP_FETCHER_H_
+#define UPDATE_ENGINE_COMMON_MULTI_RANGE_HTTP_FETCHER_H_
+
+#include <deque>
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include "update_engine/common/http_fetcher.h"
+
+// This class is a simple wrapper around an HttpFetcher. The client
+// specifies a vector of byte ranges. MultiRangeHttpFetcher will fetch bytes
+// from those offsets, using the same bash fetcher for all ranges. Thus, the
+// fetcher must support beginning a transfer after one has stopped. Pass -1
+// as a length to specify unlimited length. It really only would make sense
+// for the last range specified to have unlimited length, tho it is legal for
+// other entries to have unlimited length.
+
+// There are three states a MultiRangeHttpFetcher object will be in:
+// - Stopped (start state)
+// - Downloading
+// - Pending transfer ended
+// Various functions below that might change state indicate possible
+// state changes.
+
+namespace chromeos_update_engine {
+
+class MultiRangeHttpFetcher : public HttpFetcher, public HttpFetcherDelegate {
+ public:
+  // Takes ownership of the passed in fetcher.
+  explicit MultiRangeHttpFetcher(HttpFetcher* base_fetcher)
+      : HttpFetcher(base_fetcher->proxy_resolver()),
+        base_fetcher_(base_fetcher),
+        base_fetcher_active_(false),
+        pending_transfer_ended_(false),
+        terminating_(false),
+        current_index_(0),
+        bytes_received_this_range_(0) {}
+  ~MultiRangeHttpFetcher() override {}
+
+  void ClearRanges() { ranges_.clear(); }
+
+  void AddRange(off_t offset, size_t size) {
+    CHECK_GT(size, static_cast<size_t>(0));
+    ranges_.push_back(Range(offset, size));
+  }
+
+  void AddRange(off_t offset) {
+    ranges_.push_back(Range(offset));
+  }
+
+  // HttpFetcher overrides.
+  void SetOffset(off_t offset) override {}  // for now, doesn't support this
+
+  void SetLength(size_t length) override {}  // unsupported
+  void UnsetLength() override {}
+
+  // Begins the transfer to the specified URL.
+  // State change: Stopped -> Downloading
+  // (corner case: Stopped -> Stopped for an empty request)
+  void BeginTransfer(const std::string& url) override;
+
+  // State change: Downloading -> Pending transfer ended
+  void TerminateTransfer() override;
+
+  void Pause() override { base_fetcher_->Pause(); }
+
+  void Unpause() override { base_fetcher_->Unpause(); }
+
+  // These functions are overloaded in LibcurlHttp fetcher for testing purposes.
+  void set_idle_seconds(int seconds) override {
+    base_fetcher_->set_idle_seconds(seconds);
+  }
+  void set_retry_seconds(int seconds) override {
+    base_fetcher_->set_retry_seconds(seconds);
+  }
+  // TODO(deymo): Determine if this method should be virtual in HttpFetcher so
+  // this call is sent to the base_fetcher_.
+  virtual void SetProxies(const std::deque<std::string>& proxies) {
+    base_fetcher_->SetProxies(proxies);
+  }
+
+  inline size_t GetBytesDownloaded() override {
+    return base_fetcher_->GetBytesDownloaded();
+  }
+
+  void set_low_speed_limit(int low_speed_bps, int low_speed_sec) override {
+    base_fetcher_->set_low_speed_limit(low_speed_bps, low_speed_sec);
+  }
+
+  void set_connect_timeout(int connect_timeout_seconds) override {
+    base_fetcher_->set_connect_timeout(connect_timeout_seconds);
+  }
+
+  void set_max_retry_count(int max_retry_count) override {
+    base_fetcher_->set_max_retry_count(max_retry_count);
+  }
+
+ private:
+  // A range object defining the offset and length of a download chunk.  Zero
+  // length indicates an unspecified end offset (note that it is impossible to
+  // request a zero-length range in HTTP).
+  class Range {
+   public:
+    Range(off_t offset, size_t length) : offset_(offset), length_(length) {}
+    explicit Range(off_t offset) : offset_(offset), length_(0) {}
+
+    inline off_t offset() const { return offset_; }
+    inline size_t length() const { return length_; }
+
+    inline bool HasLength() const { return (length_ > 0); }
+
+    std::string ToString() const;
+
+   private:
+    off_t offset_;
+    size_t length_;
+  };
+
+  typedef std::vector<Range> RangesVect;
+
+  // State change: Stopped or Downloading -> Downloading
+  void StartTransfer();
+
+  // HttpFetcherDelegate overrides.
+  // State change: Downloading -> Downloading or Pending transfer ended
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes,
+                     size_t length) override;
+
+  // State change: Pending transfer ended -> Stopped
+  void TransferEnded(HttpFetcher* fetcher, bool successful);
+  // These two call TransferEnded():
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override;
+  void TransferTerminated(HttpFetcher* fetcher) override;
+
+  void Reset();
+
+  std::unique_ptr<HttpFetcher> base_fetcher_;
+
+  // If true, do not send any more data or TransferComplete to the delegate.
+  bool base_fetcher_active_;
+
+  // If true, the next fetcher needs to be started when TransferTerminated is
+  // received from the current fetcher.
+  bool pending_transfer_ended_;
+
+  // True if we are waiting for base fetcher to terminate b/c we are
+  // ourselves terminating.
+  bool terminating_;
+
+  RangesVect ranges_;
+
+  RangesVect::size_type current_index_;  // index into ranges_
+  size_t bytes_received_this_range_;
+
+  DISALLOW_COPY_AND_ASSIGN(MultiRangeHttpFetcher);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_MULTI_RANGE_HTTP_FETCHER_H_
diff --git a/common/platform_constants.h b/common/platform_constants.h
new file mode 100644
index 0000000..d1786ff
--- /dev/null
+++ b/common/platform_constants.h
@@ -0,0 +1,56 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_PLATFORM_CONSTANTS_H_
+#define UPDATE_ENGINE_COMMON_PLATFORM_CONSTANTS_H_
+
+namespace chromeos_update_engine {
+namespace constants {
+
+// The default URL used by all products when running in normal mode. The AUTest
+// URL is used when testing normal images against the alternative AUTest server.
+// Note that the URL can be override in run-time in certain cases.
+extern const char kOmahaDefaultProductionURL[];
+extern const char kOmahaDefaultAUTestURL[];
+
+// Our product name used in Omaha. This value must match the one configured in
+// the server side and is sent on every request.
+extern const char kOmahaUpdaterID[];
+
+// The name of the platform as sent to Omaha.
+extern const char kOmahaPlatformName[];
+
+// Path to the location of the public half of the payload key. The payload key
+// is used to sign the contents of the payload binary file: the manifest and the
+// whole payload.
+extern const char kUpdatePayloadPublicKeyPath[];
+
+// Path to the directory containing all the SSL certificates accepted by
+// update_engine when sending requests to Omaha and the download server (if
+// HTTPS is used for that as well).
+extern const char kCACertificatesPath[];
+
+// Path to the file used to notify chrome about the deadline of the last omaha
+// response. Empty if not supported.
+extern const char kOmahaResponseDeadlineFile[];
+
+// The stateful directory used by update_engine.
+extern const char kNonVolatileDirectory[];
+
+}  // namespace constants
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_PLATFORM_CONSTANTS_H_
diff --git a/common/platform_constants_android.cc b/common/platform_constants_android.cc
new file mode 100644
index 0000000..4f55106
--- /dev/null
+++ b/common/platform_constants_android.cc
@@ -0,0 +1,36 @@
+//
+// Copyright (C) 2015 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 "update_engine/common/platform_constants.h"
+
+namespace chromeos_update_engine {
+namespace constants {
+
+const char kOmahaDefaultProductionURL[] =
+    "https://clients2.google.com/service/update2/brillo";
+const char kOmahaDefaultAUTestURL[] =
+    "https://clients2.google.com/service/update2/brillo";
+const char kOmahaUpdaterID[] = "Brillo";
+const char kOmahaPlatformName[] = "Brillo";
+const char kUpdatePayloadPublicKeyPath[] =
+    "/etc/update_engine/update-payload-key.pub.pem";
+const char kCACertificatesPath[] = "/system/etc/security/cacerts_google";
+// No deadline file API support on Android.
+const char kOmahaResponseDeadlineFile[] = "";
+const char kNonVolatileDirectory[] = "/data/misc/update_engine";
+
+}  // namespace constants
+}  // namespace chromeos_update_engine
diff --git a/common/platform_constants_chromeos.cc b/common/platform_constants_chromeos.cc
new file mode 100644
index 0000000..d8587ca
--- /dev/null
+++ b/common/platform_constants_chromeos.cc
@@ -0,0 +1,37 @@
+//
+// Copyright (C) 2015 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 "update_engine/common/platform_constants.h"
+
+namespace chromeos_update_engine {
+namespace constants {
+
+const char kOmahaDefaultProductionURL[] =
+    "https://tools.google.com/service/update2";
+const char kOmahaDefaultAUTestURL[] =
+    "https://omaha.sandbox.google.com/service/update2";
+const char kOmahaUpdaterID[] = "ChromeOSUpdateEngine";
+const char kOmahaPlatformName[] = "Chrome OS";
+const char kUpdatePayloadPublicKeyPath[] =
+    "/usr/share/update_engine/update-payload-key.pub.pem";
+const char kCACertificatesPath[] = "/usr/share/chromeos-ca-certificates";
+const char kOmahaResponseDeadlineFile[] =
+    "/tmp/update-check-response-deadline";
+// This directory is wiped during powerwash.
+const char kNonVolatileDirectory[] = "/var/lib/update_engine";
+
+}  // namespace constants
+}  // namespace chromeos_update_engine
diff --git a/common/prefs.cc b/common/prefs.cc
new file mode 100644
index 0000000..9d3a30f
--- /dev/null
+++ b/common/prefs.cc
@@ -0,0 +1,143 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/prefs.h"
+
+#include <algorithm>
+
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+bool Prefs::Init(const base::FilePath& prefs_dir) {
+  prefs_dir_ = prefs_dir;
+  return true;
+}
+
+bool Prefs::GetString(const string& key, string* value) const {
+  base::FilePath filename;
+  TEST_AND_RETURN_FALSE(GetFileNameForKey(key, &filename));
+  if (!base::ReadFileToString(filename, value)) {
+    LOG(INFO) << key << " not present in " << prefs_dir_.value();
+    return false;
+  }
+  return true;
+}
+
+bool Prefs::SetString(const string& key, const string& value) {
+  base::FilePath filename;
+  TEST_AND_RETURN_FALSE(GetFileNameForKey(key, &filename));
+  if (!base::DirectoryExists(filename.DirName())) {
+    // Only attempt to create the directory if it doesn't exist to avoid calls
+    // to parent directories where we might not have permission to write to.
+    TEST_AND_RETURN_FALSE(base::CreateDirectory(filename.DirName()));
+  }
+  TEST_AND_RETURN_FALSE(base::WriteFile(filename, value.data(), value.size()) ==
+                        static_cast<int>(value.size()));
+  const auto observers_for_key = observers_.find(key);
+  if (observers_for_key != observers_.end()) {
+    std::vector<ObserverInterface*> copy_observers(observers_for_key->second);
+    for (ObserverInterface* observer : copy_observers)
+      observer->OnPrefSet(key);
+  }
+  return true;
+}
+
+bool Prefs::GetInt64(const string& key, int64_t* value) const {
+  string str_value;
+  if (!GetString(key, &str_value))
+    return false;
+  base::TrimWhitespaceASCII(str_value, base::TRIM_ALL, &str_value);
+  TEST_AND_RETURN_FALSE(base::StringToInt64(str_value, value));
+  return true;
+}
+
+bool Prefs::SetInt64(const string& key, const int64_t value) {
+  return SetString(key, base::Int64ToString(value));
+}
+
+bool Prefs::GetBoolean(const string& key, bool* value) const {
+  string str_value;
+  if (!GetString(key, &str_value))
+    return false;
+  base::TrimWhitespaceASCII(str_value, base::TRIM_ALL, &str_value);
+  if (str_value == "false") {
+    *value = false;
+    return true;
+  }
+  if (str_value == "true") {
+    *value = true;
+    return true;
+  }
+  return false;
+}
+
+bool Prefs::SetBoolean(const string& key, const bool value) {
+  return SetString(key, value ? "true" : "false");
+}
+
+bool Prefs::Exists(const string& key) const {
+  base::FilePath filename;
+  TEST_AND_RETURN_FALSE(GetFileNameForKey(key, &filename));
+  return base::PathExists(filename);
+}
+
+bool Prefs::Delete(const string& key) {
+  base::FilePath filename;
+  TEST_AND_RETURN_FALSE(GetFileNameForKey(key, &filename));
+  TEST_AND_RETURN_FALSE(base::DeleteFile(filename, false));
+  const auto observers_for_key = observers_.find(key);
+  if (observers_for_key != observers_.end()) {
+    std::vector<ObserverInterface*> copy_observers(observers_for_key->second);
+    for (ObserverInterface* observer : copy_observers)
+      observer->OnPrefDeleted(key);
+  }
+  return true;
+}
+
+void Prefs::AddObserver(const string& key, ObserverInterface* observer) {
+  observers_[key].push_back(observer);
+}
+
+void Prefs::RemoveObserver(const string& key, ObserverInterface* observer) {
+  std::vector<ObserverInterface*>& observers_for_key = observers_[key];
+  auto observer_it =
+      std::find(observers_for_key.begin(), observers_for_key.end(), observer);
+  if (observer_it != observers_for_key.end())
+    observers_for_key.erase(observer_it);
+}
+
+bool Prefs::GetFileNameForKey(const string& key,
+                              base::FilePath* filename) const {
+  // Allows only non-empty keys containing [A-Za-z0-9_-].
+  TEST_AND_RETURN_FALSE(!key.empty());
+  for (size_t i = 0; i < key.size(); ++i) {
+    char c = key.at(i);
+    TEST_AND_RETURN_FALSE(IsAsciiAlpha(c) || IsAsciiDigit(c) ||
+                          c == '_' || c == '-');
+  }
+  *filename = prefs_dir_.Append(key);
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/prefs.h b/common/prefs.h
new file mode 100644
index 0000000..f11abc3
--- /dev/null
+++ b/common/prefs.h
@@ -0,0 +1,81 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_PREFS_H_
+#define UPDATE_ENGINE_COMMON_PREFS_H_
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+
+#include "gtest/gtest_prod.h"  // for FRIEND_TEST
+#include "update_engine/common/prefs_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements a preference store by storing the value associated with
+// a key in a separate file named after the key under a preference
+// store directory.
+
+class Prefs : public PrefsInterface {
+ public:
+  Prefs() = default;
+
+  // Initializes the store by associating this object with |prefs_dir|
+  // as the preference store directory. Returns true on success, false
+  // otherwise.
+  bool Init(const base::FilePath& prefs_dir);
+
+  // PrefsInterface methods.
+  bool GetString(const std::string& key, std::string* value) const override;
+  bool SetString(const std::string& key, const std::string& value) override;
+  bool GetInt64(const std::string& key, int64_t* value) const override;
+  bool SetInt64(const std::string& key, const int64_t value) override;
+  bool GetBoolean(const std::string& key, bool* value) const override;
+  bool SetBoolean(const std::string& key, const bool value) override;
+
+  bool Exists(const std::string& key) const override;
+  bool Delete(const std::string& key) override;
+
+  void AddObserver(const std::string& key,
+                   ObserverInterface* observer) override;
+  void RemoveObserver(const std::string& key,
+                      ObserverInterface* observer) override;
+
+ private:
+  FRIEND_TEST(PrefsTest, GetFileNameForKey);
+  FRIEND_TEST(PrefsTest, GetFileNameForKeyBadCharacter);
+  FRIEND_TEST(PrefsTest, GetFileNameForKeyEmpty);
+
+  // Sets |filename| to the full path to the file containing the data
+  // associated with |key|. Returns true on success, false otherwise.
+  bool GetFileNameForKey(const std::string& key,
+                         base::FilePath* filename) const;
+
+  // Preference store directory.
+  base::FilePath prefs_dir_;
+
+  // The registered observers watching for changes.
+  std::map<std::string, std::vector<ObserverInterface*>> observers_;
+
+  DISALLOW_COPY_AND_ASSIGN(Prefs);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_PREFS_H_
diff --git a/common/prefs_interface.h b/common/prefs_interface.h
new file mode 100644
index 0000000..03ae3ec
--- /dev/null
+++ b/common/prefs_interface.h
@@ -0,0 +1,97 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_PREFS_INTERFACE_H_
+#define UPDATE_ENGINE_COMMON_PREFS_INTERFACE_H_
+
+#include <stdint.h>
+
+#include <string>
+
+namespace chromeos_update_engine {
+
+// The prefs interface allows access to a persistent preferences
+// store. The two reasons for providing this as an interface are
+// testing as well as easier switching to a new implementation in the
+// future, if necessary.
+
+class PrefsInterface {
+ public:
+  // Observer class to be notified about key value changes.
+  class ObserverInterface {
+   public:
+    virtual ~ObserverInterface() = default;
+
+    // Called when the value is set for the observed |key|.
+    virtual void OnPrefSet(const std::string& key) = 0;
+
+    // Called when the observed |key| is deleted.
+    virtual void OnPrefDeleted(const std::string& key) = 0;
+  };
+
+  virtual ~PrefsInterface() = default;
+
+  // Gets a string |value| associated with |key|. Returns true on
+  // success, false on failure (including when the |key| is not
+  // present in the store).
+  virtual bool GetString(const std::string& key, std::string* value) const = 0;
+
+  // Associates |key| with a string |value|. Returns true on success,
+  // false otherwise.
+  virtual bool SetString(const std::string& key, const std::string& value) = 0;
+
+  // Gets an int64_t |value| associated with |key|. Returns true on
+  // success, false on failure (including when the |key| is not
+  // present in the store).
+  virtual bool GetInt64(const std::string& key, int64_t* value) const = 0;
+
+  // Associates |key| with an int64_t |value|. Returns true on success,
+  // false otherwise.
+  virtual bool SetInt64(const std::string& key, const int64_t value) = 0;
+
+  // Gets a boolean |value| associated with |key|. Returns true on
+  // success, false on failure (including when the |key| is not
+  // present in the store).
+  virtual bool GetBoolean(const std::string& key, bool* value) const = 0;
+
+  // Associates |key| with a boolean |value|. Returns true on success,
+  // false otherwise.
+  virtual bool SetBoolean(const std::string& key, const bool value) = 0;
+
+  // Returns true if the setting exists (i.e. a file with the given key
+  // exists in the prefs directory)
+  virtual bool Exists(const std::string& key) const = 0;
+
+  // Returns true if successfully deleted the file corresponding to
+  // this key. Calling with non-existent keys does nothing.
+  virtual bool Delete(const std::string& key) = 0;
+
+  // Add an observer to watch whenever the given |key| is modified. The
+  // OnPrefSet() and OnPrefDelete() methods will be called whenever any of the
+  // Set*() methods or the Delete() method are called on the given key,
+  // respectively.
+  virtual void AddObserver(const std::string& key,
+                           ObserverInterface* observer) = 0;
+
+  // Remove an observer added with AddObserver(). The observer won't be called
+  // anymore for future Set*() and Delete() method calls.
+  virtual void RemoveObserver(const std::string& key,
+                              ObserverInterface* observer) = 0;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_PREFS_INTERFACE_H_
diff --git a/common/prefs_unittest.cc b/common/prefs_unittest.cc
new file mode 100644
index 0000000..354b05b
--- /dev/null
+++ b/common/prefs_unittest.cc
@@ -0,0 +1,337 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/prefs.h"
+
+#include <inttypes.h>
+
+#include <string>
+
+#include <base/files/file_util.h>
+#include <base/macros.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+using std::string;
+using testing::Eq;
+using testing::_;
+
+namespace {
+// Test key used along the tests.
+const char kKey[] = "test-key";
+}
+
+namespace chromeos_update_engine {
+
+class PrefsTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    ASSERT_TRUE(base::CreateNewTempDirectory("auprefs", &prefs_dir_));
+    ASSERT_TRUE(prefs_.Init(prefs_dir_));
+  }
+
+  void TearDown() override {
+    base::DeleteFile(prefs_dir_, true);  // recursive
+  }
+
+  bool SetValue(const string& key, const string& value) {
+    return base::WriteFile(prefs_dir_.Append(key), value.data(),
+                           value.length()) == static_cast<int>(value.length());
+  }
+
+  base::FilePath prefs_dir_;
+  Prefs prefs_;
+};
+
+TEST_F(PrefsTest, GetFileNameForKey) {
+  const char kAllvalidCharsKey[] =
+      "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz_-";
+  base::FilePath path;
+  EXPECT_TRUE(prefs_.GetFileNameForKey(kAllvalidCharsKey, &path));
+  EXPECT_EQ(prefs_dir_.Append(kAllvalidCharsKey).value(), path.value());
+}
+
+TEST_F(PrefsTest, GetFileNameForKeyBadCharacter) {
+  base::FilePath path;
+  EXPECT_FALSE(prefs_.GetFileNameForKey("ABC abc", &path));
+}
+
+TEST_F(PrefsTest, GetFileNameForKeyEmpty) {
+  base::FilePath path;
+  EXPECT_FALSE(prefs_.GetFileNameForKey("", &path));
+}
+
+TEST_F(PrefsTest, GetString) {
+  const string test_data = "test data";
+  ASSERT_TRUE(SetValue(kKey, test_data));
+  string value;
+  EXPECT_TRUE(prefs_.GetString(kKey, &value));
+  EXPECT_EQ(test_data, value);
+}
+
+TEST_F(PrefsTest, GetStringBadKey) {
+  string value;
+  EXPECT_FALSE(prefs_.GetString(",bad", &value));
+}
+
+TEST_F(PrefsTest, GetStringNonExistentKey) {
+  string value;
+  EXPECT_FALSE(prefs_.GetString("non-existent-key", &value));
+}
+
+TEST_F(PrefsTest, SetString) {
+  const char kValue[] = "some test value\non 2 lines";
+  EXPECT_TRUE(prefs_.SetString(kKey, kValue));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ(kValue, value);
+}
+
+TEST_F(PrefsTest, SetStringBadKey) {
+  const char kKeyWithDots[] = ".no-dots";
+  EXPECT_FALSE(prefs_.SetString(kKeyWithDots, "some value"));
+  EXPECT_FALSE(base::PathExists(prefs_dir_.Append(kKeyWithDots)));
+}
+
+TEST_F(PrefsTest, SetStringCreateDir) {
+  const char kValue[] = "test value";
+  base::FilePath subdir = prefs_dir_.Append("subdir1").Append("subdir2");
+  EXPECT_TRUE(prefs_.Init(subdir));
+  EXPECT_TRUE(prefs_.SetString(kKey, kValue));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(subdir.Append(kKey), &value));
+  EXPECT_EQ(kValue, value);
+}
+
+TEST_F(PrefsTest, SetStringDirCreationFailure) {
+  EXPECT_TRUE(prefs_.Init(base::FilePath("/dev/null")));
+  EXPECT_FALSE(prefs_.SetString(kKey, "test value"));
+}
+
+TEST_F(PrefsTest, SetStringFileCreationFailure) {
+  base::CreateDirectory(prefs_dir_.Append(kKey));
+  EXPECT_FALSE(prefs_.SetString(kKey, "test value"));
+  EXPECT_TRUE(base::DirectoryExists(prefs_dir_.Append(kKey)));
+}
+
+TEST_F(PrefsTest, GetInt64) {
+  ASSERT_TRUE(SetValue(kKey, " \n 25 \t "));
+  int64_t value;
+  EXPECT_TRUE(prefs_.GetInt64(kKey, &value));
+  EXPECT_EQ(25, value);
+}
+
+TEST_F(PrefsTest, GetInt64BadValue) {
+  ASSERT_TRUE(SetValue(kKey, "30a"));
+  int64_t value;
+  EXPECT_FALSE(prefs_.GetInt64(kKey, &value));
+}
+
+TEST_F(PrefsTest, GetInt64Max) {
+  ASSERT_TRUE(SetValue(kKey, base::StringPrintf("%" PRIi64, kint64max)));
+  int64_t value;
+  EXPECT_TRUE(prefs_.GetInt64(kKey, &value));
+  EXPECT_EQ(kint64max, value);
+}
+
+TEST_F(PrefsTest, GetInt64Min) {
+  ASSERT_TRUE(SetValue(kKey, base::StringPrintf("%" PRIi64, kint64min)));
+  int64_t value;
+  EXPECT_TRUE(prefs_.GetInt64(kKey, &value));
+  EXPECT_EQ(kint64min, value);
+}
+
+TEST_F(PrefsTest, GetInt64Negative) {
+  ASSERT_TRUE(SetValue(kKey, " \t -100 \n "));
+  int64_t value;
+  EXPECT_TRUE(prefs_.GetInt64(kKey, &value));
+  EXPECT_EQ(-100, value);
+}
+
+TEST_F(PrefsTest, GetInt64NonExistentKey) {
+  int64_t value;
+  EXPECT_FALSE(prefs_.GetInt64("random-key", &value));
+}
+
+TEST_F(PrefsTest, SetInt64) {
+  EXPECT_TRUE(prefs_.SetInt64(kKey, -123));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ("-123", value);
+}
+
+TEST_F(PrefsTest, SetInt64BadKey) {
+  const char kKeyWithSpaces[] = "s p a c e s";
+  EXPECT_FALSE(prefs_.SetInt64(kKeyWithSpaces, 20));
+  EXPECT_FALSE(base::PathExists(prefs_dir_.Append(kKeyWithSpaces)));
+}
+
+TEST_F(PrefsTest, SetInt64Max) {
+  EXPECT_TRUE(prefs_.SetInt64(kKey, kint64max));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ(base::StringPrintf("%" PRIi64, kint64max), value);
+}
+
+TEST_F(PrefsTest, SetInt64Min) {
+  EXPECT_TRUE(prefs_.SetInt64(kKey, kint64min));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ(base::StringPrintf("%" PRIi64, kint64min), value);
+}
+
+TEST_F(PrefsTest, GetBooleanFalse) {
+  ASSERT_TRUE(SetValue(kKey, " \n false \t "));
+  bool value;
+  EXPECT_TRUE(prefs_.GetBoolean(kKey, &value));
+  EXPECT_FALSE(value);
+}
+
+TEST_F(PrefsTest, GetBooleanTrue) {
+  const char kKey[] = "test-key";
+  ASSERT_TRUE(SetValue(kKey, " \t true \n "));
+  bool value;
+  EXPECT_TRUE(prefs_.GetBoolean(kKey, &value));
+  EXPECT_TRUE(value);
+}
+
+TEST_F(PrefsTest, GetBooleanBadValue) {
+  const char kKey[] = "test-key";
+  ASSERT_TRUE(SetValue(kKey, "1"));
+  bool value;
+  EXPECT_FALSE(prefs_.GetBoolean(kKey, &value));
+}
+
+TEST_F(PrefsTest, GetBooleanBadEmptyValue) {
+  const char kKey[] = "test-key";
+  ASSERT_TRUE(SetValue(kKey, ""));
+  bool value;
+  EXPECT_FALSE(prefs_.GetBoolean(kKey, &value));
+}
+
+TEST_F(PrefsTest, GetBooleanNonExistentKey) {
+  bool value;
+  EXPECT_FALSE(prefs_.GetBoolean("random-key", &value));
+}
+
+TEST_F(PrefsTest, SetBooleanTrue) {
+  const char kKey[] = "test-bool";
+  EXPECT_TRUE(prefs_.SetBoolean(kKey, true));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ("true", value);
+}
+
+TEST_F(PrefsTest, SetBooleanFalse) {
+  const char kKey[] = "test-bool";
+  EXPECT_TRUE(prefs_.SetBoolean(kKey, false));
+  string value;
+  EXPECT_TRUE(base::ReadFileToString(prefs_dir_.Append(kKey), &value));
+  EXPECT_EQ("false", value);
+}
+
+TEST_F(PrefsTest, SetBooleanBadKey) {
+  const char kKey[] = "s p a c e s";
+  EXPECT_FALSE(prefs_.SetBoolean(kKey, true));
+  EXPECT_FALSE(base::PathExists(prefs_dir_.Append(kKey)));
+}
+
+TEST_F(PrefsTest, ExistsWorks) {
+  // test that the key doesn't exist before we set it.
+  EXPECT_FALSE(prefs_.Exists(kKey));
+
+  // test that the key exists after we set it.
+  ASSERT_TRUE(prefs_.SetInt64(kKey, 8));
+  EXPECT_TRUE(prefs_.Exists(kKey));
+}
+
+TEST_F(PrefsTest, DeleteWorks) {
+  // test that it's alright to delete a non-existent key.
+  EXPECT_TRUE(prefs_.Delete(kKey));
+
+  // delete the key after we set it.
+  ASSERT_TRUE(prefs_.SetInt64(kKey, 0));
+  EXPECT_TRUE(prefs_.Delete(kKey));
+
+  // make sure it doesn't exist anymore.
+  EXPECT_FALSE(prefs_.Exists(kKey));
+}
+
+class MockPrefsObserver : public PrefsInterface::ObserverInterface {
+ public:
+  MOCK_METHOD1(OnPrefSet, void(const string&));
+  MOCK_METHOD1(OnPrefDeleted, void(const string& key));
+};
+
+TEST_F(PrefsTest, ObserversCalled) {
+  MockPrefsObserver mock_obserser;
+  prefs_.AddObserver(kKey, &mock_obserser);
+
+  EXPECT_CALL(mock_obserser, OnPrefSet(Eq(kKey)));
+  EXPECT_CALL(mock_obserser, OnPrefDeleted(_)).Times(0);
+  prefs_.SetString(kKey, "value");
+  testing::Mock::VerifyAndClearExpectations(&mock_obserser);
+
+  EXPECT_CALL(mock_obserser, OnPrefSet(_)).Times(0);
+  EXPECT_CALL(mock_obserser, OnPrefDeleted(Eq(kKey)));
+  prefs_.Delete(kKey);
+  testing::Mock::VerifyAndClearExpectations(&mock_obserser);
+
+  prefs_.RemoveObserver(kKey, &mock_obserser);
+}
+
+TEST_F(PrefsTest, OnlyCalledOnObservedKeys) {
+  MockPrefsObserver mock_obserser;
+  const char kUnusedKey[] = "unused-key";
+  prefs_.AddObserver(kUnusedKey, &mock_obserser);
+
+  EXPECT_CALL(mock_obserser, OnPrefSet(_)).Times(0);
+  EXPECT_CALL(mock_obserser, OnPrefDeleted(_)).Times(0);
+  prefs_.SetString(kKey, "value");
+  prefs_.Delete(kKey);
+
+  prefs_.RemoveObserver(kUnusedKey, &mock_obserser);
+}
+
+TEST_F(PrefsTest, RemovedObserversNotCalled) {
+  MockPrefsObserver mock_obserser_a, mock_obserser_b;
+  prefs_.AddObserver(kKey, &mock_obserser_a);
+  prefs_.AddObserver(kKey, &mock_obserser_b);
+  EXPECT_CALL(mock_obserser_a, OnPrefSet(_)).Times(2);
+  EXPECT_CALL(mock_obserser_b, OnPrefSet(_)).Times(1);
+  EXPECT_TRUE(prefs_.SetString(kKey, "value"));
+  prefs_.RemoveObserver(kKey, &mock_obserser_b);
+  EXPECT_TRUE(prefs_.SetString(kKey, "other value"));
+  prefs_.RemoveObserver(kKey, &mock_obserser_a);
+  EXPECT_TRUE(prefs_.SetString(kKey, "yet another value"));
+}
+
+TEST_F(PrefsTest, UnsuccessfulCallsNotObserved) {
+  MockPrefsObserver mock_obserser;
+  const char kInvalidKey[] = "no spaces or .";
+  prefs_.AddObserver(kInvalidKey, &mock_obserser);
+
+  EXPECT_CALL(mock_obserser, OnPrefSet(_)).Times(0);
+  EXPECT_CALL(mock_obserser, OnPrefDeleted(_)).Times(0);
+  EXPECT_FALSE(prefs_.SetString(kInvalidKey, "value"));
+  EXPECT_FALSE(prefs_.Delete(kInvalidKey));
+
+  prefs_.RemoveObserver(kInvalidKey, &mock_obserser);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/subprocess.cc b/common/subprocess.cc
new file mode 100644
index 0000000..f43aaac
--- /dev/null
+++ b/common/subprocess.cc
@@ -0,0 +1,271 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/subprocess.h"
+
+#include <fcntl.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/logging.h>
+#include <base/posix/eintr_wrapper.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/process.h>
+#include <brillo/secure_blob.h>
+
+using brillo::MessageLoop;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+bool SetupChild(const std::map<string, string>& env, uint32_t flags) {
+  // Setup the environment variables.
+  clearenv();
+  for (const auto& key_value : env) {
+    setenv(key_value.first.c_str(), key_value.second.c_str(), 0);
+  }
+
+  if ((flags & Subprocess::kRedirectStderrToStdout) != 0) {
+    if (HANDLE_EINTR(dup2(STDOUT_FILENO, STDERR_FILENO)) != STDERR_FILENO)
+      return false;
+  }
+
+  int fd = HANDLE_EINTR(open("/dev/null", O_RDONLY));
+  if (fd < 0)
+    return false;
+  if (HANDLE_EINTR(dup2(fd, STDIN_FILENO)) != STDIN_FILENO)
+    return false;
+  IGNORE_EINTR(close(fd));
+
+  return true;
+}
+
+// Helper function to launch a process with the given Subprocess::Flags.
+// This function only sets up and starts the process according to the |flags|.
+// The caller is responsible for watching the termination of the subprocess.
+// Return whether the process was successfully launched and fills in the |proc|
+// Process.
+bool LaunchProcess(const vector<string>& cmd,
+                   uint32_t flags,
+                   brillo::Process* proc) {
+  for (const string& arg : cmd)
+    proc->AddArg(arg);
+  proc->SetSearchPath((flags & Subprocess::kSearchPath) != 0);
+
+  // Create an environment for the child process with just the required PATHs.
+  std::map<string, string> env;
+  for (const char* key : {"LD_LIBRARY_PATH", "PATH"}) {
+    const char* value = getenv(key);
+    if (value)
+      env.emplace(key, value);
+  }
+
+  proc->RedirectUsingPipe(STDOUT_FILENO, false);
+  proc->SetPreExecCallback(base::Bind(&SetupChild, env, flags));
+
+  return proc->Start();
+}
+
+}  // namespace
+
+void Subprocess::Init(
+      brillo::AsynchronousSignalHandlerInterface* async_signal_handler) {
+  if (subprocess_singleton_ == this)
+    return;
+  CHECK(subprocess_singleton_ == nullptr);
+  subprocess_singleton_ = this;
+
+  process_reaper_.Register(async_signal_handler);
+}
+
+Subprocess::~Subprocess() {
+  if (subprocess_singleton_ == this)
+    subprocess_singleton_ = nullptr;
+}
+
+void Subprocess::OnStdoutReady(SubprocessRecord* record) {
+  char buf[1024];
+  ssize_t rc = 0;
+  do {
+    rc = HANDLE_EINTR(read(record->stdout_fd, buf, arraysize(buf)));
+    if (rc < 0) {
+      // EAGAIN and EWOULDBLOCK are normal return values when there's no more
+      // input as we are in non-blocking mode.
+      if (errno != EWOULDBLOCK && errno != EAGAIN) {
+        PLOG(ERROR) << "Error reading fd " << record->stdout_fd;
+        MessageLoop::current()->CancelTask(record->stdout_task_id);
+        record->stdout_task_id = MessageLoop::kTaskIdNull;
+      }
+    } else if (rc == 0) {
+      // A value of 0 means that the child closed its end of the pipe and there
+      // is nothing else to read from stdout.
+      MessageLoop::current()->CancelTask(record->stdout_task_id);
+      record->stdout_task_id = MessageLoop::kTaskIdNull;
+    } else {
+      record->stdout.append(buf, rc);
+    }
+  } while (rc > 0);
+}
+
+void Subprocess::ChildExitedCallback(const siginfo_t& info) {
+  auto pid_record = subprocess_records_.find(info.si_pid);
+  if (pid_record == subprocess_records_.end())
+    return;
+  SubprocessRecord* record = pid_record->second.get();
+
+  // Make sure we read any remaining process output and then close the pipe.
+  OnStdoutReady(record);
+
+  MessageLoop::current()->CancelTask(record->stdout_task_id);
+  record->stdout_task_id = MessageLoop::kTaskIdNull;
+
+  // Release and close all the pipes now.
+  record->proc.Release();
+  record->proc.Reset(0);
+
+  // Don't print any log if the subprocess exited with exit code 0.
+  if (info.si_code != CLD_EXITED) {
+    LOG(INFO) << "Subprocess terminated with si_code " << info.si_code;
+  } else if (info.si_status != 0) {
+    LOG(INFO) << "Subprocess exited with si_status: " << info.si_status;
+  }
+
+  if (!record->stdout.empty()) {
+    LOG(INFO) << "Subprocess output:\n" << record->stdout;
+  }
+  if (!record->callback.is_null()) {
+    record->callback.Run(info.si_status, record->stdout);
+  }
+  subprocess_records_.erase(pid_record);
+}
+
+pid_t Subprocess::Exec(const vector<string>& cmd,
+                       const ExecCallback& callback) {
+  return ExecFlags(cmd, kRedirectStderrToStdout, callback);
+}
+
+pid_t Subprocess::ExecFlags(const vector<string>& cmd,
+                            uint32_t flags,
+                            const ExecCallback& callback) {
+  unique_ptr<SubprocessRecord> record(new SubprocessRecord(callback));
+
+  if (!LaunchProcess(cmd, flags, &record->proc)) {
+    LOG(ERROR) << "Failed to launch subprocess";
+    return 0;
+  }
+
+  pid_t pid = record->proc.pid();
+  CHECK(process_reaper_.WatchForChild(FROM_HERE, pid, base::Bind(
+      &Subprocess::ChildExitedCallback,
+      base::Unretained(this))));
+
+  record->stdout_fd = record->proc.GetPipe(STDOUT_FILENO);
+  // Capture the subprocess output. Make our end of the pipe non-blocking.
+  int fd_flags = fcntl(record->stdout_fd, F_GETFL, 0) | O_NONBLOCK;
+  if (HANDLE_EINTR(fcntl(record->stdout_fd, F_SETFL, fd_flags)) < 0) {
+    LOG(ERROR) << "Unable to set non-blocking I/O mode on fd "
+               << record->stdout_fd << ".";
+  }
+
+  record->stdout_task_id = MessageLoop::current()->WatchFileDescriptor(
+      FROM_HERE,
+      record->stdout_fd,
+      MessageLoop::WatchMode::kWatchRead,
+      true,
+      base::Bind(&Subprocess::OnStdoutReady, record.get()));
+
+  subprocess_records_[pid].reset(record.release());
+  return pid;
+}
+
+void Subprocess::KillExec(pid_t pid) {
+  auto pid_record = subprocess_records_.find(pid);
+  if (pid_record == subprocess_records_.end())
+    return;
+  pid_record->second->callback.Reset();
+  kill(pid, SIGTERM);
+}
+
+bool Subprocess::SynchronousExec(const vector<string>& cmd,
+                                 int* return_code,
+                                 string* stdout) {
+  // The default for SynchronousExec is to use kSearchPath since the code relies
+  // on that.
+  return SynchronousExecFlags(
+      cmd,
+      kRedirectStderrToStdout | kSearchPath,
+      return_code,
+      stdout);
+}
+
+bool Subprocess::SynchronousExecFlags(const vector<string>& cmd,
+                                      uint32_t flags,
+                                      int* return_code,
+                                      string* stdout) {
+  brillo::ProcessImpl proc;
+  if (!LaunchProcess(cmd, flags, &proc)) {
+    LOG(ERROR) << "Failed to launch subprocess";
+    return false;
+  }
+
+  if (stdout) {
+    stdout->clear();
+  }
+
+  int fd = proc.GetPipe(STDOUT_FILENO);
+  vector<char> buffer(32 * 1024);
+  while (true) {
+    int rc = HANDLE_EINTR(read(fd, buffer.data(), buffer.size()));
+    if (rc < 0) {
+      PLOG(ERROR) << "Reading from child's output";
+      break;
+    } else if (rc == 0) {
+      break;
+    } else {
+      if (stdout)
+        stdout->append(buffer.data(), rc);
+    }
+  }
+  // At this point, the subprocess already closed the output, so we only need to
+  // wait for it to finish.
+  int proc_return_code = proc.Wait();
+  if (return_code)
+    *return_code = proc_return_code;
+  return proc_return_code != brillo::Process::kErrorExitStatus;
+}
+
+bool Subprocess::SubprocessInFlight() {
+  for (const auto& pid_record : subprocess_records_) {
+    if (!pid_record.second->callback.is_null())
+      return true;
+  }
+  return false;
+}
+
+Subprocess* Subprocess::subprocess_singleton_ = nullptr;
+
+}  // namespace chromeos_update_engine
diff --git a/common/subprocess.h b/common/subprocess.h
new file mode 100644
index 0000000..6b952dc
--- /dev/null
+++ b/common/subprocess.h
@@ -0,0 +1,141 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_SUBPROCESS_H_
+#define UPDATE_ENGINE_COMMON_SUBPROCESS_H_
+
+#include <unistd.h>
+
+#include <map>
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/callback.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/asynchronous_signal_handler_interface.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/process.h>
+#include <brillo/process_reaper.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+// The Subprocess class is a singleton. It's used to spawn off a subprocess
+// and get notified when the subprocess exits. The result of Exec() can
+// be saved and used to cancel the callback request and kill your process. If
+// you know you won't call KillExec(), you may safely lose the return value
+// from Exec().
+
+// To create the Subprocess singleton just instantiate it with and call Init().
+// You can't have two Subprocess instances initialized at the same time.
+
+namespace chromeos_update_engine {
+
+class Subprocess {
+ public:
+  enum Flags {
+    kSearchPath = 1 << 0,
+    kRedirectStderrToStdout = 1 << 1,
+  };
+
+  // Callback type used when an async process terminates. It receives the exit
+  // code and the stdout output (and stderr if redirected).
+  using ExecCallback = base::Callback<void(int, const std::string&)>;
+
+  Subprocess() = default;
+
+  // Destroy and unregister the Subprocess singleton.
+  ~Subprocess();
+
+  // Initialize and register the Subprocess singleton.
+  void Init(brillo::AsynchronousSignalHandlerInterface* async_signal_handler);
+
+  // Launches a process in the background and calls the passed |callback| when
+  // the process exits.
+  // Returns the process id of the new launched process or 0 in case of failure.
+  pid_t Exec(const std::vector<std::string>& cmd, const ExecCallback& callback);
+  pid_t ExecFlags(const std::vector<std::string>& cmd,
+                  uint32_t flags,
+                  const ExecCallback& callback);
+
+  // Kills the running process with SIGTERM and ignores the callback.
+  void KillExec(pid_t tag);
+
+  // Executes a command synchronously. Returns true on success. If |stdout| is
+  // non-null, the process output is stored in it, otherwise the output is
+  // logged. Note that stderr is redirected to stdout.
+  static bool SynchronousExec(const std::vector<std::string>& cmd,
+                              int* return_code,
+                              std::string* stdout);
+  static bool SynchronousExecFlags(const std::vector<std::string>& cmd,
+                                   uint32_t flags,
+                                   int* return_code,
+                                   std::string* stdout);
+
+  // Gets the one instance.
+  static Subprocess& Get() {
+    return *subprocess_singleton_;
+  }
+
+  // Returns true iff there is at least one subprocess we're waiting on.
+  bool SubprocessInFlight();
+
+ private:
+  FRIEND_TEST(SubprocessTest, CancelTest);
+
+  struct SubprocessRecord {
+    explicit SubprocessRecord(const ExecCallback& callback)
+      : callback(callback) {}
+
+    // The callback supplied by the caller.
+    ExecCallback callback;
+
+    // The ProcessImpl instance managing the child process. Destroying this
+    // will close our end of the pipes we have open.
+    brillo::ProcessImpl proc;
+
+    // These are used to monitor the stdout of the running process, including
+    // the stderr if it was redirected.
+    brillo::MessageLoop::TaskId stdout_task_id{
+        brillo::MessageLoop::kTaskIdNull};
+    int stdout_fd{-1};
+    std::string stdout;
+  };
+
+  // Callback which runs whenever there is input available on the subprocess
+  // stdout pipe.
+  static void OnStdoutReady(SubprocessRecord* record);
+
+  // Callback for when any subprocess terminates. This calls the user
+  // requested callback.
+  void ChildExitedCallback(const siginfo_t& info);
+
+  // The global instance.
+  static Subprocess* subprocess_singleton_;
+
+  // A map from the asynchronous subprocess tag (see Exec) to the subprocess
+  // record structure for all active asynchronous subprocesses.
+  std::map<pid_t, std::unique_ptr<SubprocessRecord>> subprocess_records_;
+
+  // Used to watch for child processes.
+  brillo::ProcessReaper process_reaper_;
+
+  DISALLOW_COPY_AND_ASSIGN(Subprocess);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_SUBPROCESS_H_
diff --git a/common/subprocess_unittest.cc b/common/subprocess_unittest.cc
new file mode 100644
index 0000000..b37dc91
--- /dev/null
+++ b/common/subprocess_unittest.cc
@@ -0,0 +1,263 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/subprocess.h"
+
+#include <fcntl.h>
+#include <netinet/in.h>
+#include <netinet/ip.h>
+#include <poll.h>
+#include <sys/socket.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/location.h>
+#include <base/message_loop/message_loop.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/base_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <brillo/strings/string_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class SubprocessTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    async_signal_handler_.Init();
+    subprocess_.Init(&async_signal_handler_);
+  }
+
+  base::MessageLoopForIO base_loop_;
+  brillo::BaseMessageLoop loop_{&base_loop_};
+  brillo::AsynchronousSignalHandler async_signal_handler_;
+  Subprocess subprocess_;
+};
+
+namespace {
+
+int local_server_port = 0;
+
+void ExpectedResults(int expected_return_code, const string& expected_output,
+                     int return_code, const string& output) {
+  EXPECT_EQ(expected_return_code, return_code);
+  EXPECT_EQ(expected_output, output);
+  MessageLoop::current()->BreakLoop();
+}
+
+void ExpectedEnvVars(int return_code, const string& output) {
+  EXPECT_EQ(0, return_code);
+  const std::set<string> allowed_envs = {"LD_LIBRARY_PATH", "PATH"};
+  for (string key_value : brillo::string_utils::Split(output, "\n")) {
+    auto key_value_pair = brillo::string_utils::SplitAtFirst(
+        key_value, "=", true);
+    EXPECT_NE(allowed_envs.end(), allowed_envs.find(key_value_pair.first));
+  }
+  MessageLoop::current()->BreakLoop();
+}
+
+}  // namespace
+
+TEST_F(SubprocessTest, IsASingleton) {
+  EXPECT_EQ(&subprocess_, &Subprocess::Get());
+}
+
+TEST_F(SubprocessTest, InactiveInstancesDontChangeTheSingleton) {
+  std::unique_ptr<Subprocess> another_subprocess(new Subprocess());
+  EXPECT_EQ(&subprocess_, &Subprocess::Get());
+  another_subprocess.reset();
+  EXPECT_EQ(&subprocess_, &Subprocess::Get());
+}
+
+TEST_F(SubprocessTest, SimpleTest) {
+  EXPECT_TRUE(subprocess_.Exec({"/bin/false"},
+                               base::Bind(&ExpectedResults, 1, "")));
+  loop_.Run();
+}
+
+TEST_F(SubprocessTest, EchoTest) {
+  EXPECT_TRUE(subprocess_.Exec(
+      {"/bin/sh", "-c", "echo this is stdout; echo this is stderr >&2"},
+      base::Bind(&ExpectedResults, 0, "this is stdout\nthis is stderr\n")));
+  loop_.Run();
+}
+
+TEST_F(SubprocessTest, StderrNotIncludedInOutputTest) {
+  EXPECT_TRUE(subprocess_.ExecFlags(
+      {"/bin/sh", "-c", "echo on stdout; echo on stderr >&2"},
+      0,
+      base::Bind(&ExpectedResults, 0, "on stdout\n")));
+  loop_.Run();
+}
+
+TEST_F(SubprocessTest, EnvVarsAreFiltered) {
+  EXPECT_TRUE(subprocess_.Exec({"/usr/bin/env"}, base::Bind(&ExpectedEnvVars)));
+  loop_.Run();
+}
+
+TEST_F(SubprocessTest, SynchronousTrueSearchsOnPath) {
+  int rc = -1;
+  EXPECT_TRUE(Subprocess::SynchronousExecFlags(
+      {"true"}, Subprocess::kSearchPath, &rc, nullptr));
+  EXPECT_EQ(0, rc);
+}
+
+TEST_F(SubprocessTest, SynchronousEchoTest) {
+  vector<string> cmd = {
+    "/bin/sh",
+    "-c",
+    "echo -n stdout-here; echo -n stderr-there > /dev/stderr"};
+  int rc = -1;
+  string stdout;
+  ASSERT_TRUE(Subprocess::SynchronousExec(cmd, &rc, &stdout));
+  EXPECT_EQ(0, rc);
+  EXPECT_EQ("stdout-herestderr-there", stdout);
+}
+
+TEST_F(SubprocessTest, SynchronousEchoNoOutputTest) {
+  int rc = -1;
+  ASSERT_TRUE(Subprocess::SynchronousExec(
+      {"/bin/sh", "-c", "echo test"},
+      &rc, nullptr));
+  EXPECT_EQ(0, rc);
+}
+
+namespace {
+void CallbackBad(int return_code, const string& output) {
+  ADD_FAILURE() << "should never be called.";
+}
+
+// TODO(garnold) this test method uses test_http_server as a representative for
+// interactive processes that can be spawned/terminated at will. This causes us
+// to go through hoops when spawning this process (e.g. obtaining the port
+// number it uses so we can control it with wget). It would have been much
+// preferred to use something else and thus simplify both test_http_server
+// (doesn't have to be able to communicate through a temp file) and the test
+// code below; for example, it sounds like a brain dead sleep loop with proper
+// signal handlers could be used instead.
+void StartAndCancelInRunLoop(bool* spawned) {
+  // Create a temp file for test_http_server to communicate its port number.
+  char temp_file_name[] = "/tmp/subprocess_unittest-test_http_server-XXXXXX";
+  int temp_fd = mkstemp(temp_file_name);
+  CHECK_GE(temp_fd, 0);
+  int temp_flags = fcntl(temp_fd, F_GETFL, 0) | O_NONBLOCK;
+  CHECK_EQ(fcntl(temp_fd, F_SETFL, temp_flags), 0);
+
+  vector<string> cmd;
+  cmd.push_back("./test_http_server");
+  cmd.push_back(temp_file_name);
+  uint32_t tag = Subprocess::Get().Exec(cmd, base::Bind(&CallbackBad));
+  EXPECT_NE(0, tag);
+  *spawned = true;
+  printf("test http server spawned\n");
+  // Wait for server to be up and running
+  TimeDelta total_wait_time;
+  const TimeDelta kSleepTime = TimeDelta::FromMilliseconds(100);
+  const TimeDelta kMaxWaitTime = TimeDelta::FromSeconds(3);
+  local_server_port = 0;
+  static const char* kServerListeningMsgPrefix = "listening on port ";
+  while (total_wait_time.InMicroseconds() < kMaxWaitTime.InMicroseconds()) {
+    char line[80];
+    int line_len = read(temp_fd, line, sizeof(line) - 1);
+    if (line_len > 0) {
+      line[line_len] = '\0';
+      CHECK_EQ(strstr(line, kServerListeningMsgPrefix), line);
+      const char* listening_port_str =
+          line + strlen(kServerListeningMsgPrefix);
+      char* end_ptr;
+      long raw_port = strtol(listening_port_str,  // NOLINT(runtime/int)
+                             &end_ptr, 10);
+      CHECK(!*end_ptr || *end_ptr == '\n');
+      local_server_port = static_cast<in_port_t>(raw_port);
+      break;
+    } else if (line_len < 0 && errno != EAGAIN) {
+      LOG(INFO) << "error reading from " << temp_file_name << ": "
+                << strerror(errno);
+      break;
+    }
+    usleep(kSleepTime.InMicroseconds());
+    total_wait_time += kSleepTime;
+  }
+  close(temp_fd);
+  remove(temp_file_name);
+  CHECK_GT(local_server_port, 0);
+  LOG(INFO) << "server listening on port " << local_server_port;
+  Subprocess::Get().KillExec(tag);
+}
+
+void ExitWhenDone(bool* spawned) {
+  if (*spawned && !Subprocess::Get().SubprocessInFlight()) {
+    // tear down the sub process
+    printf("tear down time\n");
+    int status = test_utils::System(
+        base::StringPrintf("wget -O /dev/null http://127.0.0.1:%d/quitquitquit",
+                           local_server_port));
+    EXPECT_NE(-1, status) << "system() failed";
+    EXPECT_TRUE(WIFEXITED(status))
+        << "command failed to run or died abnormally";
+    MessageLoop::current()->BreakLoop();
+  } else {
+    // Re-run this callback again in 10 ms.
+    MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&ExitWhenDone, spawned),
+        TimeDelta::FromMilliseconds(10));
+  }
+}
+
+}  // namespace
+
+TEST_F(SubprocessTest, CancelTest) {
+  bool spawned = false;
+  loop_.PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&StartAndCancelInRunLoop, &spawned),
+      TimeDelta::FromMilliseconds(100));
+  loop_.PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&ExitWhenDone, &spawned),
+      TimeDelta::FromMilliseconds(10));
+  loop_.Run();
+  // This test would leak a callback that runs when the child process exits
+  // unless we wait for it to run.
+  brillo::MessageLoopRunUntil(
+      &loop_,
+      TimeDelta::FromSeconds(10),
+      base::Bind([] {
+        return Subprocess::Get().subprocess_records_.empty();
+      }));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/terminator.cc b/common/terminator.cc
new file mode 100644
index 0000000..62adafd
--- /dev/null
+++ b/common/terminator.cc
@@ -0,0 +1,56 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/terminator.h"
+
+#include <cstdlib>
+
+namespace chromeos_update_engine {
+
+volatile sig_atomic_t Terminator::exit_status_ = 1;  // default exit status
+volatile sig_atomic_t Terminator::exit_blocked_ = 0;
+volatile sig_atomic_t Terminator::exit_requested_ = 0;
+
+void Terminator::Init() {
+  exit_blocked_ = 0;
+  exit_requested_ = 0;
+  signal(SIGTERM, HandleSignal);
+}
+
+void Terminator::Init(int exit_status) {
+  exit_status_ = exit_status;
+  Init();
+}
+
+void Terminator::Exit() {
+  exit(exit_status_);
+}
+
+void Terminator::HandleSignal(int signum) {
+  if (exit_blocked_ == 0) {
+    Exit();
+  }
+  exit_requested_ = 1;
+}
+
+ScopedTerminatorExitUnblocker::~ScopedTerminatorExitUnblocker() {
+  Terminator::set_exit_blocked(false);
+  if (Terminator::exit_requested()) {
+    Terminator::Exit();
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/terminator.h b/common/terminator.h
new file mode 100644
index 0000000..20616f6
--- /dev/null
+++ b/common/terminator.h
@@ -0,0 +1,65 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_TERMINATOR_H_
+#define UPDATE_ENGINE_COMMON_TERMINATOR_H_
+
+#include <signal.h>
+
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+namespace chromeos_update_engine {
+
+// A class allowing graceful delayed exit.
+class Terminator {
+ public:
+  // Initializes the terminator and sets up signal handlers.
+  static void Init();
+  static void Init(int exit_status);
+
+  // Terminates the current process.
+  static void Exit();
+
+  // Set to true if the terminator should block termination requests in an
+  // attempt to block exiting.
+  static void set_exit_blocked(bool block) { exit_blocked_ = block ? 1 : 0; }
+  static bool exit_blocked() { return exit_blocked_ != 0; }
+
+  // Returns true if the system is trying to terminate the process, false
+  // otherwise. Returns true only if exit was blocked when the termination
+  // request arrived.
+  static bool exit_requested() { return exit_requested_ != 0; }
+
+ private:
+  FRIEND_TEST(TerminatorTest, HandleSignalTest);
+  FRIEND_TEST(TerminatorDeathTest, ScopedTerminatorExitUnblockerExitTest);
+
+  // The signal handler.
+  static void HandleSignal(int signum);
+
+  static volatile sig_atomic_t exit_status_;
+  static volatile sig_atomic_t exit_blocked_;
+  static volatile sig_atomic_t exit_requested_;
+};
+
+class ScopedTerminatorExitUnblocker {
+ public:
+  ~ScopedTerminatorExitUnblocker();
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_TERMINATOR_H_
diff --git a/common/terminator_unittest.cc b/common/terminator_unittest.cc
new file mode 100644
index 0000000..5e8302f
--- /dev/null
+++ b/common/terminator_unittest.cc
@@ -0,0 +1,85 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/terminator.h"
+
+#include <gtest/gtest.h>
+#include <gtest/gtest-spi.h>
+
+using testing::ExitedWithCode;
+
+namespace chromeos_update_engine {
+
+class TerminatorTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    Terminator::Init();
+    ASSERT_FALSE(Terminator::exit_blocked());
+    ASSERT_FALSE(Terminator::exit_requested());
+  }
+  void TearDown() override {
+    // Makes sure subsequent non-Terminator tests don't get accidentally
+    // terminated.
+    Terminator::Init();
+  }
+};
+
+typedef TerminatorTest TerminatorDeathTest;
+
+namespace {
+void UnblockExitThroughUnblocker() {
+  ScopedTerminatorExitUnblocker unblocker = ScopedTerminatorExitUnblocker();
+}
+
+void RaiseSIGTERM() {
+  ASSERT_EXIT(raise(SIGTERM), ExitedWithCode(2), "");
+}
+}  // namespace
+
+TEST_F(TerminatorTest, HandleSignalTest) {
+  Terminator::set_exit_blocked(true);
+  Terminator::HandleSignal(SIGTERM);
+  ASSERT_TRUE(Terminator::exit_requested());
+}
+
+TEST_F(TerminatorTest, ScopedTerminatorExitUnblockerTest) {
+  Terminator::set_exit_blocked(true);
+  ASSERT_TRUE(Terminator::exit_blocked());
+  ASSERT_FALSE(Terminator::exit_requested());
+  UnblockExitThroughUnblocker();
+  ASSERT_FALSE(Terminator::exit_blocked());
+  ASSERT_FALSE(Terminator::exit_requested());
+}
+
+TEST_F(TerminatorDeathTest, ExitTest) {
+  ASSERT_EXIT(Terminator::Exit(), ExitedWithCode(2), "");
+  Terminator::set_exit_blocked(true);
+  ASSERT_EXIT(Terminator::Exit(), ExitedWithCode(2), "");
+}
+
+TEST_F(TerminatorDeathTest, RaiseSignalTest) {
+  RaiseSIGTERM();
+  Terminator::set_exit_blocked(true);
+  EXPECT_FATAL_FAILURE(RaiseSIGTERM(), "");
+}
+
+TEST_F(TerminatorDeathTest, ScopedTerminatorExitUnblockerExitTest) {
+  Terminator::set_exit_blocked(true);
+  Terminator::exit_requested_ = 1;
+  ASSERT_EXIT(UnblockExitThroughUnblocker(), ExitedWithCode(2), "");
+}
+
+}  // namespace chromeos_update_engine
diff --git a/common/test_utils.cc b/common/test_utils.cc
new file mode 100644
index 0000000..f89c448
--- /dev/null
+++ b/common/test_utils.cc
@@ -0,0 +1,268 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/test_utils.h"
+
+#include <dirent.h>
+#include <errno.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <sys/xattr.h>
+#include <unistd.h>
+
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/format_macros.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/file_writer.h"
+
+using base::StringPrintf;
+using std::set;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+void PrintTo(const Extent& extent, ::std::ostream* os) {
+  *os << "(" << extent.start_block() << ", " << extent.num_blocks() << ")";
+}
+
+namespace test_utils {
+
+const char* const kMountPathTemplate = "UpdateEngineTests_mnt-XXXXXX";
+
+const uint8_t kRandomString[] = {
+  0xf2, 0xb7, 0x55, 0x92, 0xea, 0xa6, 0xc9, 0x57,
+  0xe0, 0xf8, 0xeb, 0x34, 0x93, 0xd9, 0xc4, 0x8f,
+  0xcb, 0x20, 0xfa, 0x37, 0x4b, 0x40, 0xcf, 0xdc,
+  0xa5, 0x08, 0x70, 0x89, 0x79, 0x35, 0xe2, 0x3d,
+  0x56, 0xa4, 0x75, 0x73, 0xa3, 0x6d, 0xd1, 0xd5,
+  0x26, 0xbb, 0x9c, 0x60, 0xbd, 0x2f, 0x5a, 0xfa,
+  0xb7, 0xd4, 0x3a, 0x50, 0xa7, 0x6b, 0x3e, 0xfd,
+  0x61, 0x2b, 0x3a, 0x31, 0x30, 0x13, 0x33, 0x53,
+  0xdb, 0xd0, 0x32, 0x71, 0x5c, 0x39, 0xed, 0xda,
+  0xb4, 0x84, 0xca, 0xbc, 0xbd, 0x78, 0x1c, 0x0c,
+  0xd8, 0x0b, 0x41, 0xe8, 0xe1, 0xe0, 0x41, 0xad,
+  0x03, 0x12, 0xd3, 0x3d, 0xb8, 0x75, 0x9b, 0xe6,
+  0xd9, 0x01, 0xd0, 0x87, 0xf4, 0x36, 0xfa, 0xa7,
+  0x0a, 0xfa, 0xc5, 0x87, 0x65, 0xab, 0x9a, 0x7b,
+  0xeb, 0x58, 0x23, 0xf0, 0xa8, 0x0a, 0xf2, 0x33,
+  0x3a, 0xe2, 0xe3, 0x35, 0x74, 0x95, 0xdd, 0x3c,
+  0x59, 0x5a, 0xd9, 0x52, 0x3a, 0x3c, 0xac, 0xe5,
+  0x15, 0x87, 0x6d, 0x82, 0xbc, 0xf8, 0x7d, 0xbe,
+  0xca, 0xd3, 0x2c, 0xd6, 0xec, 0x38, 0xeb, 0xe4,
+  0x53, 0xb0, 0x4c, 0x3f, 0x39, 0x29, 0xf7, 0xa4,
+  0x73, 0xa8, 0xcb, 0x32, 0x50, 0x05, 0x8c, 0x1c,
+  0x1c, 0xca, 0xc9, 0x76, 0x0b, 0x8f, 0x6b, 0x57,
+  0x1f, 0x24, 0x2b, 0xba, 0x82, 0xba, 0xed, 0x58,
+  0xd8, 0xbf, 0xec, 0x06, 0x64, 0x52, 0x6a, 0x3f,
+  0xe4, 0xad, 0xce, 0x84, 0xb4, 0x27, 0x55, 0x14,
+  0xe3, 0x75, 0x59, 0x73, 0x71, 0x51, 0xea, 0xe8,
+  0xcc, 0xda, 0x4f, 0x09, 0xaf, 0xa4, 0xbc, 0x0e,
+  0xa6, 0x1f, 0xe2, 0x3a, 0xf8, 0x96, 0x7d, 0x30,
+  0x23, 0xc5, 0x12, 0xb5, 0xd8, 0x73, 0x6b, 0x71,
+  0xab, 0xf1, 0xd7, 0x43, 0x58, 0xa7, 0xc9, 0xf0,
+  0xe4, 0x85, 0x1c, 0xd6, 0x92, 0x50, 0x2c, 0x98,
+  0x36, 0xfe, 0x87, 0xaf, 0x43, 0x8f, 0x8f, 0xf5,
+  0x88, 0x48, 0x18, 0x42, 0xcf, 0x42, 0xc1, 0xa8,
+  0xe8, 0x05, 0x08, 0xa1, 0x45, 0x70, 0x5b, 0x8c,
+  0x39, 0x28, 0xab, 0xe9, 0x6b, 0x51, 0xd2, 0xcb,
+  0x30, 0x04, 0xea, 0x7d, 0x2f, 0x6e, 0x6c, 0x3b,
+  0x5f, 0x82, 0xd9, 0x5b, 0x89, 0x37, 0x65, 0x65,
+  0xbe, 0x9f, 0xa3, 0x5d,
+};
+
+bool IsXAttrSupported(const base::FilePath& dir_path) {
+  char *path = strdup(dir_path.Append("xattr_test_XXXXXX").value().c_str());
+
+  int fd = mkstemp(path);
+  if (fd == -1) {
+    PLOG(ERROR) << "Error creating temporary file in " << dir_path.value();
+    free(path);
+    return false;
+  }
+
+  if (unlink(path) != 0) {
+    PLOG(ERROR) << "Error unlinking temporary file " << path;
+    close(fd);
+    free(path);
+    return false;
+  }
+
+  int xattr_res = fsetxattr(fd, "user.xattr-test", "value", strlen("value"), 0);
+  if (xattr_res != 0) {
+    if (errno == ENOTSUP) {
+      // Leave it to call-sites to warn about non-support.
+    } else {
+      PLOG(ERROR) << "Error setting xattr on " << path;
+    }
+  }
+  close(fd);
+  free(path);
+  return xattr_res == 0;
+}
+
+bool WriteFileVector(const string& path, const brillo::Blob& data) {
+  return utils::WriteFile(path.c_str(), data.data(), data.size());
+}
+
+bool WriteFileString(const string& path, const string& data) {
+  return utils::WriteFile(path.c_str(), data.data(), data.size());
+}
+
+// Binds provided |filename| to an unused loopback device, whose name is written
+// to the string pointed to by |lo_dev_name_p|. Returns true on success, false
+// otherwise (along with corresponding test failures), in which case the content
+// of |lo_dev_name_p| is unknown.
+bool BindToUnusedLoopDevice(const string& filename, string* lo_dev_name_p) {
+  CHECK(lo_dev_name_p);
+
+  // Bind to an unused loopback device, sanity check the device name.
+  lo_dev_name_p->clear();
+  if (!(utils::ReadPipe("losetup --show -f " + filename, lo_dev_name_p) &&
+        base::StartsWithASCII(*lo_dev_name_p, "/dev/loop", true))) {
+    ADD_FAILURE();
+    return false;
+  }
+
+  // Strip anything from the first newline char.
+  size_t newline_pos = lo_dev_name_p->find('\n');
+  if (newline_pos != string::npos)
+    lo_dev_name_p->erase(newline_pos);
+
+  return true;
+}
+
+bool ExpectVectorsEq(const brillo::Blob& expected,
+                     const brillo::Blob& actual) {
+  EXPECT_EQ(expected.size(), actual.size());
+  if (expected.size() != actual.size())
+    return false;
+  bool is_all_eq = true;
+  for (unsigned int i = 0; i < expected.size(); i++) {
+    EXPECT_EQ(expected[i], actual[i]) << "offset: " << i;
+    is_all_eq = is_all_eq && (expected[i] == actual[i]);
+  }
+  return is_all_eq;
+}
+
+void FillWithData(brillo::Blob* buffer) {
+  size_t input_counter = 0;
+  for (uint8_t& b : *buffer) {
+    b = kRandomString[input_counter];
+    input_counter++;
+    input_counter %= sizeof(kRandomString);
+  }
+}
+
+void CreateEmptyExtImageAtPath(const string& path,
+                               size_t size,
+                               int block_size) {
+  EXPECT_EQ(0, System(StringPrintf("dd if=/dev/zero of=%s"
+                                   " seek=%" PRIuS " bs=1 count=1 status=none",
+                                   path.c_str(), size)));
+  EXPECT_EQ(0, System(StringPrintf("mkfs.ext3 -q -b %d -F %s",
+                                   block_size, path.c_str())));
+}
+
+void CreateExtImageAtPath(const string& path, vector<string>* out_paths) {
+  // create 10MiB sparse file, mounted at a unique location.
+  string mount_path;
+  CHECK(utils::MakeTempDirectory(kMountPathTemplate, &mount_path));
+  ScopedDirRemover mount_path_unlinker(mount_path);
+
+  EXPECT_EQ(0, System(StringPrintf("dd if=/dev/zero of=%s"
+                                   " seek=10485759 bs=1 count=1 status=none",
+                                   path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mkfs.ext3 -q -b 4096 -F %s",
+                                   path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mount -o loop %s %s", path.c_str(),
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("echo hi > %s/hi", mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("echo hello > %s/hello",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mkdir %s/some_dir", mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mkdir %s/some_dir/empty_dir",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mkdir %s/some_dir/mnt",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("echo T > %s/some_dir/test",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mkfifo %s/some_dir/fifo",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("mknod %s/cdev c 2 3", mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("ln -s /some/target %s/sym",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("ln %s/some_dir/test %s/testlink",
+                                   mount_path.c_str(), mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("echo T > %s/srchardlink0",
+                                   mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("ln %s/srchardlink0 %s/srchardlink1",
+                                   mount_path.c_str(), mount_path.c_str())));
+  EXPECT_EQ(0, System(StringPrintf("ln -s bogus %s/boguslink",
+                                   mount_path.c_str())));
+  EXPECT_TRUE(utils::UnmountFilesystem(mount_path.c_str()));
+
+  if (out_paths) {
+    out_paths->clear();
+    out_paths->push_back("");
+    out_paths->push_back("/hi");
+    out_paths->push_back("/boguslink");
+    out_paths->push_back("/hello");
+    out_paths->push_back("/some_dir");
+    out_paths->push_back("/some_dir/empty_dir");
+    out_paths->push_back("/some_dir/mnt");
+    out_paths->push_back("/some_dir/test");
+    out_paths->push_back("/some_dir/fifo");
+    out_paths->push_back("/cdev");
+    out_paths->push_back("/testlink");
+    out_paths->push_back("/sym");
+    out_paths->push_back("/srchardlink0");
+    out_paths->push_back("/srchardlink1");
+    out_paths->push_back("/lost+found");
+  }
+}
+
+ScopedLoopMounter::ScopedLoopMounter(const string& file_path,
+                                     string* mnt_path,
+                                     unsigned long flags) {  // NOLINT - long
+  EXPECT_TRUE(utils::MakeTempDirectory("mnt.XXXXXX", mnt_path));
+  dir_remover_.reset(new ScopedDirRemover(*mnt_path));
+
+  string loop_dev;
+  loop_binder_.reset(new ScopedLoopbackDeviceBinder(file_path, &loop_dev));
+
+  EXPECT_TRUE(utils::MountFilesystem(loop_dev, *mnt_path, flags));
+  unmounter_.reset(new ScopedFilesystemUnmounter(*mnt_path));
+}
+
+base::FilePath GetBuildArtifactsPath() {
+  base::FilePath exe_path;
+  base::ReadSymbolicLink(base::FilePath("/proc/self/exe"), &exe_path);
+  return exe_path.DirName();
+}
+
+}  // namespace test_utils
+}  // namespace chromeos_update_engine
diff --git a/common/test_utils.h b/common/test_utils.h
new file mode 100644
index 0000000..616bdd3
--- /dev/null
+++ b/common/test_utils.h
@@ -0,0 +1,271 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_TEST_UTILS_H_
+#define UPDATE_ENGINE_COMMON_TEST_UTILS_H_
+
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+// Streams used for gtest's PrintTo() functions.
+#include <iostream>  // NOLINT(readability/streams)
+#include <memory>
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/callback.h>
+#include <base/files/file_path.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_metadata.pb.h"
+
+// These are some handy functions for unittests.
+
+namespace chromeos_update_engine {
+
+// PrintTo() functions are used by gtest to log these objects. These PrintTo()
+// functions must be defined in the same namespace as the first argument.
+void PrintTo(const Extent& extent, ::std::ostream* os);
+
+namespace test_utils {
+
+// 300 byte pseudo-random string. Not null terminated.
+// This does not gzip compress well.
+extern const uint8_t kRandomString[300];
+
+// Writes the data passed to path. The file at path will be overwritten if it
+// exists. Returns true on success, false otherwise.
+bool WriteFileVector(const std::string& path, const brillo::Blob& data);
+bool WriteFileString(const std::string& path, const std::string& data);
+
+bool BindToUnusedLoopDevice(const std::string &filename,
+                            std::string* lo_dev_name_ptr);
+
+// Returns true iff a == b
+bool ExpectVectorsEq(const brillo::Blob& a, const brillo::Blob& b);
+
+inline int System(const std::string& cmd) {
+  return system(cmd.c_str());
+}
+
+inline int Symlink(const std::string& oldpath, const std::string& newpath) {
+  return symlink(oldpath.c_str(), newpath.c_str());
+}
+
+inline int Chmod(const std::string& path, mode_t mode) {
+  return chmod(path.c_str(), mode);
+}
+
+inline int Mkdir(const std::string& path, mode_t mode) {
+  return mkdir(path.c_str(), mode);
+}
+
+inline int Chdir(const std::string& path) {
+  return chdir(path.c_str());
+}
+
+// Checks if xattr is supported in the directory specified by
+// |dir_path| which must be writable. Returns true if the feature is
+// supported, false if not or if an error occurred.
+bool IsXAttrSupported(const base::FilePath& dir_path);
+
+void FillWithData(brillo::Blob* buffer);
+
+// Creates an empty ext image.
+void CreateEmptyExtImageAtPath(const std::string& path,
+                               size_t size,
+                               int block_size);
+
+// Creates an ext image with some files in it. The paths creates are
+// returned in out_paths.
+void CreateExtImageAtPath(const std::string& path,
+                          std::vector<std::string>* out_paths);
+
+// Class to unmount FS when object goes out of scope
+class ScopedFilesystemUnmounter {
+ public:
+  explicit ScopedFilesystemUnmounter(const std::string& mountpoint)
+      : mountpoint_(mountpoint),
+        should_unmount_(true) {}
+  ~ScopedFilesystemUnmounter() {
+    if (should_unmount_) {
+      utils::UnmountFilesystem(mountpoint_);
+    }
+  }
+  void set_should_unmount(bool unmount) { should_unmount_ = unmount; }
+ private:
+  const std::string mountpoint_;
+  bool should_unmount_;
+  DISALLOW_COPY_AND_ASSIGN(ScopedFilesystemUnmounter);
+};
+
+class ScopedLoopbackDeviceBinder {
+ public:
+  ScopedLoopbackDeviceBinder(const std::string& file, std::string* dev) {
+    is_bound_ = BindToUnusedLoopDevice(file, &dev_);
+    EXPECT_TRUE(is_bound_);
+
+    if (is_bound_ && dev)
+      *dev = dev_;
+  }
+
+  ~ScopedLoopbackDeviceBinder() {
+    if (!is_bound_)
+      return;
+
+    for (int retry = 0; retry < 5; retry++) {
+      std::vector<std::string> args;
+      args.push_back("/sbin/losetup");
+      args.push_back("-d");
+      args.push_back(dev_);
+      int return_code = 0;
+      EXPECT_TRUE(Subprocess::SynchronousExec(args, &return_code, nullptr));
+      if (return_code == 0) {
+        return;
+      }
+      sleep(1);
+    }
+    ADD_FAILURE();
+  }
+
+  const std::string &dev() {
+    EXPECT_TRUE(is_bound_);
+    return dev_;
+  }
+
+  bool is_bound() const { return is_bound_; }
+
+ private:
+  std::string dev_;
+  bool is_bound_;
+  DISALLOW_COPY_AND_ASSIGN(ScopedLoopbackDeviceBinder);
+};
+
+class ScopedTempFile {
+ public:
+  ScopedTempFile() {
+    EXPECT_TRUE(utils::MakeTempFile("update_engine_test_temp_file.XXXXXX",
+                                    &path_,
+                                    nullptr));
+    unlinker_.reset(new ScopedPathUnlinker(path_));
+  }
+  const std::string& GetPath() { return path_; }
+ private:
+  std::string path_;
+  std::unique_ptr<ScopedPathUnlinker> unlinker_;
+};
+
+class ScopedLoopMounter {
+ public:
+  explicit ScopedLoopMounter(const std::string& file_path,
+                             std::string* mnt_path,
+                             unsigned long flags);  // NOLINT(runtime/int)
+
+ private:
+  // These objects must be destructed in the following order:
+  //   ScopedFilesystemUnmounter (the file system must be unmounted first)
+  //   ScopedLoopbackDeviceBinder (then the loop device can be deleted)
+  //   ScopedDirRemover (then the mount point can be deleted)
+  std::unique_ptr<ScopedDirRemover> dir_remover_;
+  std::unique_ptr<ScopedLoopbackDeviceBinder> loop_binder_;
+  std::unique_ptr<ScopedFilesystemUnmounter> unmounter_;
+};
+
+// Returns the path where the build artifacts are stored. This is the directory
+// where the unittest executable is being run from.
+base::FilePath GetBuildArtifactsPath();
+
+}  // namespace test_utils
+
+// Useful actions for test. These need to be defined in the
+// chromeos_update_engine namespace.
+
+class NoneType;
+
+template<typename T>
+class ObjectFeederAction;
+
+template<typename T>
+class ActionTraits<ObjectFeederAction<T>> {
+ public:
+  typedef T OutputObjectType;
+  typedef NoneType InputObjectType;
+};
+
+// This is a simple Action class for testing. It feeds an object into
+// another action.
+template<typename T>
+class ObjectFeederAction : public Action<ObjectFeederAction<T>> {
+ public:
+  typedef NoneType InputObjectType;
+  typedef T OutputObjectType;
+  void PerformAction() {
+    LOG(INFO) << "feeder running!";
+    CHECK(this->processor_);
+    if (this->HasOutputPipe()) {
+      this->SetOutputObject(out_obj_);
+    }
+    this->processor_->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  static std::string StaticType() { return "ObjectFeederAction"; }
+  std::string Type() const { return StaticType(); }
+  void set_obj(const T& out_obj) {
+    out_obj_ = out_obj;
+  }
+ private:
+  T out_obj_;
+};
+
+template<typename T>
+class ObjectCollectorAction;
+
+template<typename T>
+class ActionTraits<ObjectCollectorAction<T>> {
+ public:
+  typedef NoneType OutputObjectType;
+  typedef T InputObjectType;
+};
+
+// This is a simple Action class for testing. It receives an object from
+// another action.
+template<typename T>
+class ObjectCollectorAction : public Action<ObjectCollectorAction<T>> {
+ public:
+  typedef T InputObjectType;
+  typedef NoneType OutputObjectType;
+  void PerformAction() {
+    LOG(INFO) << "collector running!";
+    ASSERT_TRUE(this->processor_);
+    if (this->HasInputObject()) {
+      object_ = this->GetInputObject();
+    }
+    this->processor_->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  static std::string StaticType() { return "ObjectCollectorAction"; }
+  std::string Type() const { return StaticType(); }
+  const T& object() const { return object_; }
+ private:
+  T object_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_COMMON_TEST_UTILS_H_
diff --git a/common/utils.cc b/common/utils.cc
new file mode 100644
index 0000000..f1a357b
--- /dev/null
+++ b/common/utils.cc
@@ -0,0 +1,1302 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/utils.h"
+
+#include <stdint.h>
+
+#include <dirent.h>
+#include <elf.h>
+#include <endian.h>
+#include <errno.h>
+#include <ext2fs/ext2fs.h>
+#include <fcntl.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/mount.h>
+#include <sys/resource.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <sys/wait.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <utility>
+#include <vector>
+
+#include <base/callback.h>
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/files/scoped_file.h>
+#include <base/format_macros.h>
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/posix/eintr_wrapper.h>
+#include <base/rand_util.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_split.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/data_encoding.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/payload_consumer/file_descriptor.h"
+#include "update_engine/payload_consumer/file_writer.h"
+
+using base::Time;
+using base::TimeDelta;
+using std::min;
+using std::pair;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// The following constants control how UnmountFilesystem should retry if
+// umount() fails with an errno EBUSY, i.e. retry 5 times over the course of
+// one second.
+const int kUnmountMaxNumOfRetries = 5;
+const int kUnmountRetryIntervalInMicroseconds = 200 * 1000;  // 200 ms
+
+// Number of bytes to read from a file to attempt to detect its contents. Used
+// in GetFileFormat.
+const int kGetFileFormatMaxHeaderSize = 32;
+
+// The path to the kernel's boot_id.
+const char kBootIdPath[] = "/proc/sys/kernel/random/boot_id";
+
+// Return true if |disk_name| is an MTD or a UBI device. Note that this test is
+// simply based on the name of the device.
+bool IsMtdDeviceName(const string& disk_name) {
+  return base::StartsWithASCII(disk_name, "/dev/ubi", true) ||
+         base::StartsWithASCII(disk_name, "/dev/mtd", true);
+}
+
+// Return the device name for the corresponding partition on a NAND device.
+// WARNING: This function returns device names that are not mountable.
+string MakeNandPartitionName(int partition_num) {
+  switch (partition_num) {
+    case 2:
+    case 4:
+    case 6: {
+      return base::StringPrintf("/dev/mtd%d", partition_num);
+    }
+    default: {
+      return base::StringPrintf("/dev/ubi%d_0", partition_num);
+    }
+  }
+}
+
+// Return the device name for the corresponding partition on a NAND device that
+// may be mountable (but may not be writable).
+string MakeNandPartitionNameForMount(int partition_num) {
+  switch (partition_num) {
+    case 2:
+    case 4:
+    case 6: {
+      return base::StringPrintf("/dev/mtd%d", partition_num);
+    }
+    case 3:
+    case 5:
+    case 7: {
+      return base::StringPrintf("/dev/ubiblock%d_0", partition_num);
+    }
+    default: {
+      return base::StringPrintf("/dev/ubi%d_0", partition_num);
+    }
+  }
+}
+
+// If |path| is absolute, or explicit relative to the current working directory,
+// leaves it as is. Otherwise, uses the system's temp directory, as defined by
+// base::GetTempDir() and prepends it to |path|. On success stores the full
+// temporary path in |template_path| and returns true.
+bool GetTempName(const string& path, base::FilePath* template_path) {
+  if (path[0] == '/' || base::StartsWithASCII(path, "./", true) ||
+      base::StartsWithASCII(path, "../", true)) {
+    *template_path = base::FilePath(path);
+    return true;
+  }
+
+  base::FilePath temp_dir;
+#ifdef __ANDROID__
+  temp_dir = base::FilePath(constants::kNonVolatileDirectory).Append("tmp");
+  if (!base::PathExists(temp_dir))
+    TEST_AND_RETURN_FALSE(base::CreateDirectory(temp_dir));
+#else
+  TEST_AND_RETURN_FALSE(base::GetTempDir(&temp_dir));
+#endif  // __ANDROID__
+  *template_path = temp_dir.Append(path);
+  return true;
+}
+
+}  // namespace
+
+namespace utils {
+
+// Cgroup container is created in update-engine's upstart script located at
+// /etc/init/update-engine.conf.
+static const char kCGroupDir[] = "/sys/fs/cgroup/cpu/update-engine";
+
+string ParseECVersion(string input_line) {
+  base::TrimWhitespaceASCII(input_line, base::TRIM_ALL, &input_line);
+
+  // At this point we want to convert the format key=value pair from mosys to
+  // a vector of key value pairs.
+  vector<pair<string, string>> kv_pairs;
+  if (base::SplitStringIntoKeyValuePairs(input_line, '=', ' ', &kv_pairs)) {
+    for (const pair<string, string>& kv_pair : kv_pairs) {
+      // Finally match against the fw_verion which may have quotes.
+      if (kv_pair.first == "fw_version") {
+        string output;
+        // Trim any quotes.
+        base::TrimString(kv_pair.second, "\"", &output);
+        return output;
+      }
+    }
+  }
+  LOG(ERROR) << "Unable to parse fwid from ec info.";
+  return "";
+}
+
+bool WriteFile(const char* path, const void* data, int data_len) {
+  DirectFileWriter writer;
+  TEST_AND_RETURN_FALSE_ERRNO(0 == writer.Open(path,
+                                               O_WRONLY | O_CREAT | O_TRUNC,
+                                               0600));
+  ScopedFileWriterCloser closer(&writer);
+  TEST_AND_RETURN_FALSE_ERRNO(writer.Write(data, data_len));
+  return true;
+}
+
+bool WriteAll(int fd, const void* buf, size_t count) {
+  const char* c_buf = static_cast<const char*>(buf);
+  ssize_t bytes_written = 0;
+  while (bytes_written < static_cast<ssize_t>(count)) {
+    ssize_t rc = write(fd, c_buf + bytes_written, count - bytes_written);
+    TEST_AND_RETURN_FALSE_ERRNO(rc >= 0);
+    bytes_written += rc;
+  }
+  return true;
+}
+
+bool PWriteAll(int fd, const void* buf, size_t count, off_t offset) {
+  const char* c_buf = static_cast<const char*>(buf);
+  size_t bytes_written = 0;
+  int num_attempts = 0;
+  while (bytes_written < count) {
+    num_attempts++;
+    ssize_t rc = pwrite(fd, c_buf + bytes_written, count - bytes_written,
+                        offset + bytes_written);
+    // TODO(garnold) for debugging failure in chromium-os:31077; to be removed.
+    if (rc < 0) {
+      PLOG(ERROR) << "pwrite error; num_attempts=" << num_attempts
+                  << " bytes_written=" << bytes_written
+                  << " count=" << count << " offset=" << offset;
+    }
+    TEST_AND_RETURN_FALSE_ERRNO(rc >= 0);
+    bytes_written += rc;
+  }
+  return true;
+}
+
+bool WriteAll(FileDescriptorPtr fd, const void* buf, size_t count) {
+  const char* c_buf = static_cast<const char*>(buf);
+  ssize_t bytes_written = 0;
+  while (bytes_written < static_cast<ssize_t>(count)) {
+    ssize_t rc = fd->Write(c_buf + bytes_written, count - bytes_written);
+    TEST_AND_RETURN_FALSE_ERRNO(rc >= 0);
+    bytes_written += rc;
+  }
+  return true;
+}
+
+bool PWriteAll(FileDescriptorPtr fd,
+               const void* buf,
+               size_t count,
+               off_t offset) {
+  TEST_AND_RETURN_FALSE_ERRNO(fd->Seek(offset, SEEK_SET) !=
+                              static_cast<off_t>(-1));
+  return WriteAll(fd, buf, count);
+}
+
+bool PReadAll(int fd, void* buf, size_t count, off_t offset,
+              ssize_t* out_bytes_read) {
+  char* c_buf = static_cast<char*>(buf);
+  ssize_t bytes_read = 0;
+  while (bytes_read < static_cast<ssize_t>(count)) {
+    ssize_t rc = pread(fd, c_buf + bytes_read, count - bytes_read,
+                       offset + bytes_read);
+    TEST_AND_RETURN_FALSE_ERRNO(rc >= 0);
+    if (rc == 0) {
+      break;
+    }
+    bytes_read += rc;
+  }
+  *out_bytes_read = bytes_read;
+  return true;
+}
+
+bool PReadAll(FileDescriptorPtr fd, void* buf, size_t count, off_t offset,
+              ssize_t* out_bytes_read) {
+  TEST_AND_RETURN_FALSE_ERRNO(fd->Seek(offset, SEEK_SET) !=
+                              static_cast<off_t>(-1));
+  char* c_buf = static_cast<char*>(buf);
+  ssize_t bytes_read = 0;
+  while (bytes_read < static_cast<ssize_t>(count)) {
+    ssize_t rc = fd->Read(c_buf + bytes_read, count - bytes_read);
+    TEST_AND_RETURN_FALSE_ERRNO(rc >= 0);
+    if (rc == 0) {
+      break;
+    }
+    bytes_read += rc;
+  }
+  *out_bytes_read = bytes_read;
+  return true;
+}
+
+// Append |nbytes| of content from |buf| to the vector pointed to by either
+// |vec_p| or |str_p|.
+static void AppendBytes(const uint8_t* buf, size_t nbytes,
+                        brillo::Blob* vec_p) {
+  CHECK(buf);
+  CHECK(vec_p);
+  vec_p->insert(vec_p->end(), buf, buf + nbytes);
+}
+static void AppendBytes(const uint8_t* buf, size_t nbytes,
+                        string* str_p) {
+  CHECK(buf);
+  CHECK(str_p);
+  str_p->append(buf, buf + nbytes);
+}
+
+// Reads from an open file |fp|, appending the read content to the container
+// pointer to by |out_p|.  Returns true upon successful reading all of the
+// file's content, false otherwise. If |size| is not -1, reads up to |size|
+// bytes.
+template <class T>
+static bool Read(FILE* fp, off_t size, T* out_p) {
+  CHECK(fp);
+  CHECK(size == -1 || size >= 0);
+  uint8_t buf[1024];
+  while (size == -1 || size > 0) {
+    off_t bytes_to_read = sizeof(buf);
+    if (size > 0 && bytes_to_read > size) {
+      bytes_to_read = size;
+    }
+    size_t nbytes = fread(buf, 1, bytes_to_read, fp);
+    if (!nbytes) {
+      break;
+    }
+    AppendBytes(buf, nbytes, out_p);
+    if (size != -1) {
+      CHECK(size >= static_cast<off_t>(nbytes));
+      size -= nbytes;
+    }
+  }
+  if (ferror(fp)) {
+    return false;
+  }
+  return size == 0 || feof(fp);
+}
+
+// Opens a file |path| for reading and appends its the contents to a container
+// |out_p|. Starts reading the file from |offset|. If |offset| is beyond the end
+// of the file, returns success. If |size| is not -1, reads up to |size| bytes.
+template <class T>
+static bool ReadFileChunkAndAppend(const string& path,
+                                   off_t offset,
+                                   off_t size,
+                                   T* out_p) {
+  CHECK_GE(offset, 0);
+  CHECK(size == -1 || size >= 0);
+  base::ScopedFILE fp(fopen(path.c_str(), "r"));
+  if (!fp.get())
+    return false;
+  if (offset) {
+    // Return success without appending any data if a chunk beyond the end of
+    // the file is requested.
+    if (offset >= FileSize(path)) {
+      return true;
+    }
+    TEST_AND_RETURN_FALSE_ERRNO(fseek(fp.get(), offset, SEEK_SET) == 0);
+  }
+  return Read(fp.get(), size, out_p);
+}
+
+// TODO(deymo): This is only used in unittest, but requires the private
+// Read<string>() defined here. Expose Read<string>() or move to base/ version.
+bool ReadPipe(const string& cmd, string* out_p) {
+  FILE* fp = popen(cmd.c_str(), "r");
+  if (!fp)
+    return false;
+  bool success = Read(fp, -1, out_p);
+  return (success && pclose(fp) >= 0);
+}
+
+bool ReadFile(const string& path, brillo::Blob* out_p) {
+  return ReadFileChunkAndAppend(path, 0, -1, out_p);
+}
+
+bool ReadFile(const string& path, string* out_p) {
+  return ReadFileChunkAndAppend(path, 0, -1, out_p);
+}
+
+bool ReadFileChunk(const string& path, off_t offset, off_t size,
+                   brillo::Blob* out_p) {
+  return ReadFileChunkAndAppend(path, offset, size, out_p);
+}
+
+off_t BlockDevSize(int fd) {
+  uint64_t dev_size;
+  int rc = ioctl(fd, BLKGETSIZE64, &dev_size);
+  if (rc == -1) {
+    dev_size = -1;
+    PLOG(ERROR) << "Error running ioctl(BLKGETSIZE64) on " << fd;
+  }
+  return dev_size;
+}
+
+off_t FileSize(int fd) {
+  struct stat stbuf;
+  int rc = fstat(fd, &stbuf);
+  CHECK_EQ(rc, 0);
+  if (rc < 0) {
+    PLOG(ERROR) << "Error stat-ing " << fd;
+    return rc;
+  }
+  if (S_ISREG(stbuf.st_mode))
+    return stbuf.st_size;
+  if (S_ISBLK(stbuf.st_mode))
+    return BlockDevSize(fd);
+  LOG(ERROR) << "Couldn't determine the type of " << fd;
+  return -1;
+}
+
+off_t FileSize(const string& path) {
+  int fd = open(path.c_str(), O_RDONLY | O_CLOEXEC);
+  if (fd == -1) {
+    PLOG(ERROR) << "Error opening " << path;
+    return fd;
+  }
+  off_t size = FileSize(fd);
+  if (size == -1)
+    PLOG(ERROR) << "Error getting file size of " << path;
+  close(fd);
+  return size;
+}
+
+void HexDumpArray(const uint8_t* const arr, const size_t length) {
+  LOG(INFO) << "Logging array of length: " << length;
+  const unsigned int bytes_per_line = 16;
+  for (uint32_t i = 0; i < length; i += bytes_per_line) {
+    const unsigned int bytes_remaining = length - i;
+    const unsigned int bytes_per_this_line = min(bytes_per_line,
+                                                 bytes_remaining);
+    char header[100];
+    int r = snprintf(header, sizeof(header), "0x%08x : ", i);
+    TEST_AND_RETURN(r == 13);
+    string line = header;
+    for (unsigned int j = 0; j < bytes_per_this_line; j++) {
+      char buf[20];
+      uint8_t c = arr[i + j];
+      r = snprintf(buf, sizeof(buf), "%02x ", static_cast<unsigned int>(c));
+      TEST_AND_RETURN(r == 3);
+      line += buf;
+    }
+    LOG(INFO) << line;
+  }
+}
+
+bool SplitPartitionName(const string& partition_name,
+                        string* out_disk_name,
+                        int* out_partition_num) {
+  if (!base::StartsWithASCII(partition_name, "/dev/", true)) {
+    LOG(ERROR) << "Invalid partition device name: " << partition_name;
+    return false;
+  }
+
+  size_t last_nondigit_pos = partition_name.find_last_not_of("0123456789");
+  if (last_nondigit_pos == string::npos ||
+      (last_nondigit_pos + 1) == partition_name.size()) {
+    LOG(ERROR) << "Unable to parse partition device name: " << partition_name;
+    return false;
+  }
+
+  size_t partition_name_len = string::npos;
+  if (partition_name[last_nondigit_pos] == '_') {
+    // NAND block devices have weird naming which could be something
+    // like "/dev/ubiblock2_0". We discard "_0" in such a case.
+    size_t prev_nondigit_pos =
+        partition_name.find_last_not_of("0123456789", last_nondigit_pos - 1);
+    if (prev_nondigit_pos == string::npos ||
+        (prev_nondigit_pos + 1) == last_nondigit_pos) {
+      LOG(ERROR) << "Unable to parse partition device name: " << partition_name;
+      return false;
+    }
+
+    partition_name_len = last_nondigit_pos - prev_nondigit_pos;
+    last_nondigit_pos = prev_nondigit_pos;
+  }
+
+  if (out_disk_name) {
+    // Special case for MMC devices which have the following naming scheme:
+    // mmcblk0p2
+    size_t disk_name_len = last_nondigit_pos;
+    if (partition_name[last_nondigit_pos] != 'p' ||
+        last_nondigit_pos == 0 ||
+        !isdigit(partition_name[last_nondigit_pos - 1])) {
+      disk_name_len++;
+    }
+    *out_disk_name = partition_name.substr(0, disk_name_len);
+  }
+
+  if (out_partition_num) {
+    string partition_str = partition_name.substr(last_nondigit_pos + 1,
+                                                 partition_name_len);
+    *out_partition_num = atoi(partition_str.c_str());
+  }
+  return true;
+}
+
+string MakePartitionName(const string& disk_name, int partition_num) {
+  if (partition_num < 1) {
+    LOG(ERROR) << "Invalid partition number: " << partition_num;
+    return string();
+  }
+
+  if (!base::StartsWithASCII(disk_name, "/dev/", true)) {
+    LOG(ERROR) << "Invalid disk name: " << disk_name;
+    return string();
+  }
+
+  if (IsMtdDeviceName(disk_name)) {
+    // Special case for UBI block devices.
+    //   1. ubiblock is not writable, we need to use plain "ubi".
+    //   2. There is a "_0" suffix.
+    return MakeNandPartitionName(partition_num);
+  }
+
+  string partition_name = disk_name;
+  if (isdigit(partition_name.back())) {
+    // Special case for devices with names ending with a digit.
+    // Add "p" to separate the disk name from partition number,
+    // e.g. "/dev/loop0p2"
+    partition_name += 'p';
+  }
+
+  partition_name += std::to_string(partition_num);
+
+  return partition_name;
+}
+
+string MakePartitionNameForMount(const string& part_name) {
+  if (IsMtdDeviceName(part_name)) {
+    int partition_num;
+    if (!SplitPartitionName(part_name, nullptr, &partition_num)) {
+      return "";
+    }
+    return MakeNandPartitionNameForMount(partition_num);
+  }
+  return part_name;
+}
+
+string ErrnoNumberAsString(int err) {
+  char buf[100];
+  buf[0] = '\0';
+  return strerror_r(err, buf, sizeof(buf));
+}
+
+bool FileExists(const char* path) {
+  struct stat stbuf;
+  return 0 == lstat(path, &stbuf);
+}
+
+bool IsSymlink(const char* path) {
+  struct stat stbuf;
+  return lstat(path, &stbuf) == 0 && S_ISLNK(stbuf.st_mode) != 0;
+}
+
+bool TryAttachingUbiVolume(int volume_num, int timeout) {
+  const string volume_path = base::StringPrintf("/dev/ubi%d_0", volume_num);
+  if (FileExists(volume_path.c_str())) {
+    return true;
+  }
+
+  int exit_code;
+  vector<string> cmd = {
+      "ubiattach",
+      "-m",
+      base::StringPrintf("%d", volume_num),
+      "-d",
+      base::StringPrintf("%d", volume_num)
+  };
+  TEST_AND_RETURN_FALSE(Subprocess::SynchronousExec(cmd, &exit_code, nullptr));
+  TEST_AND_RETURN_FALSE(exit_code == 0);
+
+  cmd = {
+      "ubiblock",
+      "--create",
+      volume_path
+  };
+  TEST_AND_RETURN_FALSE(Subprocess::SynchronousExec(cmd, &exit_code, nullptr));
+  TEST_AND_RETURN_FALSE(exit_code == 0);
+
+  while (timeout > 0 && !FileExists(volume_path.c_str())) {
+    sleep(1);
+    timeout--;
+  }
+
+  return FileExists(volume_path.c_str());
+}
+
+bool MakeTempFile(const string& base_filename_template,
+                  string* filename,
+                  int* fd) {
+  base::FilePath filename_template;
+  TEST_AND_RETURN_FALSE(
+      GetTempName(base_filename_template, &filename_template));
+  DCHECK(filename || fd);
+  vector<char> buf(filename_template.value().size() + 1);
+  memcpy(buf.data(), filename_template.value().data(),
+         filename_template.value().size());
+  buf[filename_template.value().size()] = '\0';
+
+  int mkstemp_fd = mkstemp(buf.data());
+  TEST_AND_RETURN_FALSE_ERRNO(mkstemp_fd >= 0);
+  if (filename) {
+    *filename = buf.data();
+  }
+  if (fd) {
+    *fd = mkstemp_fd;
+  } else {
+    close(mkstemp_fd);
+  }
+  return true;
+}
+
+bool MakeTempDirectory(const string& base_dirname_template,
+                       string* dirname) {
+  base::FilePath dirname_template;
+  TEST_AND_RETURN_FALSE(GetTempName(base_dirname_template, &dirname_template));
+  DCHECK(dirname);
+  vector<char> buf(dirname_template.value().size() + 1);
+  memcpy(buf.data(), dirname_template.value().data(),
+         dirname_template.value().size());
+  buf[dirname_template.value().size()] = '\0';
+
+  char* return_code = mkdtemp(buf.data());
+  TEST_AND_RETURN_FALSE_ERRNO(return_code != nullptr);
+  *dirname = buf.data();
+  return true;
+}
+
+bool MountFilesystem(const string& device,
+                     const string& mountpoint,
+                     unsigned long mountflags) {  // NOLINT(runtime/int)
+  // TODO(sosa): Remove "ext3" once crbug.com/208022 is resolved.
+  const vector<const char*> fstypes{"ext2", "ext3", "ext4", "squashfs"};
+  for (const char* fstype : fstypes) {
+    int rc = mount(device.c_str(), mountpoint.c_str(), fstype, mountflags,
+                   nullptr);
+    if (rc == 0)
+      return true;
+
+    PLOG(WARNING) << "Unable to mount destination device " << device
+                  << " on " << mountpoint << " as " << fstype;
+  }
+  LOG(ERROR) << "Unable to mount " << device << " with any supported type";
+  return false;
+}
+
+bool UnmountFilesystem(const string& mountpoint) {
+  for (int num_retries = 0; ; ++num_retries) {
+    if (umount(mountpoint.c_str()) == 0)
+      break;
+
+    TEST_AND_RETURN_FALSE_ERRNO(errno == EBUSY &&
+                                num_retries < kUnmountMaxNumOfRetries);
+    usleep(kUnmountRetryIntervalInMicroseconds);
+  }
+  return true;
+}
+
+bool GetFilesystemSize(const string& device,
+                       int* out_block_count,
+                       int* out_block_size) {
+  int fd = HANDLE_EINTR(open(device.c_str(), O_RDONLY));
+  TEST_AND_RETURN_FALSE_ERRNO(fd >= 0);
+  ScopedFdCloser fd_closer(&fd);
+  return GetFilesystemSizeFromFD(fd, out_block_count, out_block_size);
+}
+
+bool GetFilesystemSizeFromFD(int fd,
+                             int* out_block_count,
+                             int* out_block_size) {
+  TEST_AND_RETURN_FALSE(fd >= 0);
+
+  // Determine the filesystem size by directly reading the block count and
+  // block size information from the superblock. Supported FS are ext3 and
+  // squashfs.
+
+  // Read from the fd only once and detect in memory. The first 2 KiB is enough
+  // to read the ext2 superblock (located at offset 1024) and the squashfs
+  // superblock (located at offset 0).
+  const ssize_t kBufferSize = 2048;
+
+  uint8_t buffer[kBufferSize];
+  if (HANDLE_EINTR(pread(fd, buffer, kBufferSize, 0)) != kBufferSize) {
+    PLOG(ERROR) << "Unable to read the file system header:";
+    return false;
+  }
+
+  if (GetSquashfs4Size(buffer, kBufferSize, out_block_count, out_block_size))
+    return true;
+  if (GetExt3Size(buffer, kBufferSize, out_block_count, out_block_size))
+    return true;
+
+  LOG(ERROR) << "Unable to determine file system type.";
+  return false;
+}
+
+bool GetExt3Size(const uint8_t* buffer, size_t buffer_size,
+                 int* out_block_count,
+                 int* out_block_size) {
+  // See include/linux/ext2_fs.h for more details on the structure. We obtain
+  // ext2 constants from ext2fs/ext2fs.h header but we don't link with the
+  // library.
+  if (buffer_size < SUPERBLOCK_OFFSET + SUPERBLOCK_SIZE)
+    return false;
+
+  const uint8_t* superblock = buffer + SUPERBLOCK_OFFSET;
+
+  // ext3_fs.h: ext3_super_block.s_blocks_count
+  uint32_t block_count =
+      *reinterpret_cast<const uint32_t*>(superblock + 1 * sizeof(int32_t));
+
+  // ext3_fs.h: ext3_super_block.s_log_block_size
+  uint32_t log_block_size =
+      *reinterpret_cast<const uint32_t*>(superblock + 6 * sizeof(int32_t));
+
+  // ext3_fs.h: ext3_super_block.s_magic
+  uint16_t magic =
+      *reinterpret_cast<const uint16_t*>(superblock + 14 * sizeof(int32_t));
+
+  block_count = le32toh(block_count);
+  log_block_size = le32toh(log_block_size) + EXT2_MIN_BLOCK_LOG_SIZE;
+  magic = le16toh(magic);
+
+  // Sanity check the parameters.
+  TEST_AND_RETURN_FALSE(magic == EXT2_SUPER_MAGIC);
+  TEST_AND_RETURN_FALSE(log_block_size >= EXT2_MIN_BLOCK_LOG_SIZE &&
+                        log_block_size <= EXT2_MAX_BLOCK_LOG_SIZE);
+  TEST_AND_RETURN_FALSE(block_count > 0);
+
+  if (out_block_count)
+    *out_block_count = block_count;
+  if (out_block_size)
+    *out_block_size = 1 << log_block_size;
+  return true;
+}
+
+bool GetSquashfs4Size(const uint8_t* buffer, size_t buffer_size,
+                      int* out_block_count,
+                      int* out_block_size) {
+  // See fs/squashfs/squashfs_fs.h for format details. We only support
+  // Squashfs 4.x little endian.
+
+  // sizeof(struct squashfs_super_block)
+  const size_t kSquashfsSuperBlockSize = 96;
+  if (buffer_size < kSquashfsSuperBlockSize)
+    return false;
+
+  // Check magic, squashfs_fs.h: SQUASHFS_MAGIC
+  if (memcmp(buffer, "hsqs", 4) != 0)
+    return false;  // Only little endian is supported.
+
+  // squashfs_fs.h: struct squashfs_super_block.s_major
+  uint16_t s_major = *reinterpret_cast<const uint16_t*>(
+      buffer + 5 * sizeof(uint32_t) + 4 * sizeof(uint16_t));
+
+  if (s_major != 4) {
+    LOG(ERROR) << "Found unsupported squashfs major version " << s_major;
+    return false;
+  }
+
+  // squashfs_fs.h: struct squashfs_super_block.bytes_used
+  uint64_t bytes_used = *reinterpret_cast<const int64_t*>(
+      buffer + 5 * sizeof(uint32_t) + 6 * sizeof(uint16_t) + sizeof(uint64_t));
+
+  const int block_size = 4096;
+
+  // The squashfs' bytes_used doesn't need to be aligned with the block boundary
+  // so we round up to the nearest blocksize.
+  if (out_block_count)
+    *out_block_count = (bytes_used + block_size - 1) / block_size;
+  if (out_block_size)
+    *out_block_size = block_size;
+  return true;
+}
+
+bool IsExtFilesystem(const string& device) {
+  brillo::Blob header;
+  // The first 2 KiB is enough to read the ext2 superblock (located at offset
+  // 1024).
+  if (!ReadFileChunk(device, 0, 2048, &header))
+    return false;
+  return GetExt3Size(header.data(), header.size(), nullptr, nullptr);
+}
+
+bool IsSquashfsFilesystem(const string& device) {
+  brillo::Blob header;
+  // The first 96 is enough to read the squashfs superblock.
+  const ssize_t kSquashfsSuperBlockSize = 96;
+  if (!ReadFileChunk(device, 0, kSquashfsSuperBlockSize, &header))
+    return false;
+  return GetSquashfs4Size(header.data(), header.size(), nullptr, nullptr);
+}
+
+// Tries to parse the header of an ELF file to obtain a human-readable
+// description of it on the |output| string.
+static bool GetFileFormatELF(const uint8_t* buffer, size_t size,
+                             string* output) {
+  // 0x00: EI_MAG - ELF magic header, 4 bytes.
+  if (size < SELFMAG || memcmp(buffer, ELFMAG, SELFMAG) != 0)
+    return false;
+  *output = "ELF";
+
+  // 0x04: EI_CLASS, 1 byte.
+  if (size < EI_CLASS + 1)
+    return true;
+  switch (buffer[EI_CLASS]) {
+    case ELFCLASS32:
+      *output += " 32-bit";
+      break;
+    case ELFCLASS64:
+      *output += " 64-bit";
+      break;
+    default:
+      *output += " ?-bit";
+  }
+
+  // 0x05: EI_DATA, endianness, 1 byte.
+  if (size < EI_DATA + 1)
+    return true;
+  uint8_t ei_data = buffer[EI_DATA];
+  switch (ei_data) {
+    case ELFDATA2LSB:
+      *output += " little-endian";
+      break;
+    case ELFDATA2MSB:
+      *output += " big-endian";
+      break;
+    default:
+      *output += " ?-endian";
+      // Don't parse anything after the 0x10 offset if endianness is unknown.
+      return true;
+  }
+
+  const Elf32_Ehdr* hdr = reinterpret_cast<const Elf32_Ehdr*>(buffer);
+  // 0x12: e_machine, 2 byte endianness based on ei_data. The position (0x12)
+  // and size is the same for both 32 and 64 bits.
+  if (size < offsetof(Elf32_Ehdr, e_machine) + sizeof(hdr->e_machine))
+    return true;
+  uint16_t e_machine;
+  // Fix endianess regardless of the host endianess.
+  if (ei_data == ELFDATA2LSB)
+    e_machine = le16toh(hdr->e_machine);
+  else
+    e_machine = be16toh(hdr->e_machine);
+
+  switch (e_machine) {
+    case EM_386:
+      *output += " x86";
+      break;
+    case EM_MIPS:
+      *output += " mips";
+      break;
+    case EM_ARM:
+      *output += " arm";
+      break;
+    case EM_X86_64:
+      *output += " x86-64";
+      break;
+    default:
+      *output += " unknown-arch";
+  }
+  return true;
+}
+
+string GetFileFormat(const string& path) {
+  brillo::Blob buffer;
+  if (!ReadFileChunkAndAppend(path, 0, kGetFileFormatMaxHeaderSize, &buffer))
+    return "File not found.";
+
+  string result;
+  if (GetFileFormatELF(buffer.data(), buffer.size(), &result))
+    return result;
+
+  return "data";
+}
+
+namespace {
+// Do the actual trigger. We do it as a main-loop callback to (try to) get a
+// consistent stack trace.
+void TriggerCrashReporterUpload() {
+  pid_t pid = fork();
+  CHECK_GE(pid, 0) << "fork failed";  // fork() failed. Something is very wrong.
+  if (pid == 0) {
+    // We are the child. Crash.
+    abort();  // never returns
+  }
+  // We are the parent. Wait for child to terminate.
+  pid_t result = waitpid(pid, nullptr, 0);
+  LOG_IF(ERROR, result < 0) << "waitpid() failed";
+}
+}  // namespace
+
+void ScheduleCrashReporterUpload() {
+  brillo::MessageLoop::current()->PostTask(
+      FROM_HERE,
+      base::Bind(&TriggerCrashReporterUpload));
+}
+
+bool SetCpuShares(CpuShares shares) {
+  string string_shares = base::IntToString(static_cast<int>(shares));
+  string cpu_shares_file = string(utils::kCGroupDir) + "/cpu.shares";
+  LOG(INFO) << "Setting cgroup cpu shares to  " << string_shares;
+  if (utils::WriteFile(cpu_shares_file.c_str(), string_shares.c_str(),
+                       string_shares.size())) {
+    return true;
+  } else {
+    LOG(ERROR) << "Failed to change cgroup cpu shares to "<< string_shares
+               << " using " << cpu_shares_file;
+    return false;
+  }
+}
+
+int FuzzInt(int value, unsigned int range) {
+  int min = value - range / 2;
+  int max = value + range - range / 2;
+  return base::RandInt(min, max);
+}
+
+string FormatSecs(unsigned secs) {
+  return FormatTimeDelta(TimeDelta::FromSeconds(secs));
+}
+
+string FormatTimeDelta(TimeDelta delta) {
+  string str;
+
+  // Handle negative durations by prefixing with a minus.
+  if (delta.ToInternalValue() < 0) {
+    delta *= -1;
+    str = "-";
+  }
+
+  // Canonicalize into days, hours, minutes, seconds and microseconds.
+  unsigned days = delta.InDays();
+  delta -= TimeDelta::FromDays(days);
+  unsigned hours = delta.InHours();
+  delta -= TimeDelta::FromHours(hours);
+  unsigned mins = delta.InMinutes();
+  delta -= TimeDelta::FromMinutes(mins);
+  unsigned secs = delta.InSeconds();
+  delta -= TimeDelta::FromSeconds(secs);
+  unsigned usecs = delta.InMicroseconds();
+
+  if (days)
+    base::StringAppendF(&str, "%ud", days);
+  if (days || hours)
+    base::StringAppendF(&str, "%uh", hours);
+  if (days || hours || mins)
+    base::StringAppendF(&str, "%um", mins);
+  base::StringAppendF(&str, "%u", secs);
+  if (usecs) {
+    int width = 6;
+    while ((usecs / 10) * 10 == usecs) {
+      usecs /= 10;
+      width--;
+    }
+    base::StringAppendF(&str, ".%0*u", width, usecs);
+  }
+  base::StringAppendF(&str, "s");
+  return str;
+}
+
+string ToString(const Time utc_time) {
+  Time::Exploded exp_time;
+  utc_time.UTCExplode(&exp_time);
+  return base::StringPrintf("%d/%d/%d %d:%02d:%02d GMT",
+                      exp_time.month,
+                      exp_time.day_of_month,
+                      exp_time.year,
+                      exp_time.hour,
+                      exp_time.minute,
+                      exp_time.second);
+}
+
+string ToString(bool b) {
+  return (b ? "true" : "false");
+}
+
+string ToString(DownloadSource source) {
+  switch (source) {
+    case kDownloadSourceHttpsServer: return "HttpsServer";
+    case kDownloadSourceHttpServer:  return "HttpServer";
+    case kDownloadSourceHttpPeer:    return "HttpPeer";
+    case kNumDownloadSources:        return "Unknown";
+    // Don't add a default case to let the compiler warn about newly added
+    // download sources which should be added here.
+  }
+
+  return "Unknown";
+}
+
+string ToString(PayloadType payload_type) {
+  switch (payload_type) {
+    case kPayloadTypeDelta:      return "Delta";
+    case kPayloadTypeFull:       return "Full";
+    case kPayloadTypeForcedFull: return "ForcedFull";
+    case kNumPayloadTypes:       return "Unknown";
+    // Don't add a default case to let the compiler warn about newly added
+    // payload types which should be added here.
+  }
+
+  return "Unknown";
+}
+
+ErrorCode GetBaseErrorCode(ErrorCode code) {
+  // Ignore the higher order bits in the code by applying the mask as
+  // we want the enumerations to be in the small contiguous range
+  // with values less than ErrorCode::kUmaReportedMax.
+  ErrorCode base_code = static_cast<ErrorCode>(
+      static_cast<int>(code) & ~static_cast<int>(ErrorCode::kSpecialFlags));
+
+  // Make additional adjustments required for UMA and error classification.
+  // TODO(jaysri): Move this logic to UeErrorCode.cc when we fix
+  // chromium-os:34369.
+  if (base_code >= ErrorCode::kOmahaRequestHTTPResponseBase) {
+    // Since we want to keep the enums to a small value, aggregate all HTTP
+    // errors into this one bucket for UMA and error classification purposes.
+    LOG(INFO) << "Converting error code " << base_code
+              << " to ErrorCode::kOmahaErrorInHTTPResponse";
+    base_code = ErrorCode::kOmahaErrorInHTTPResponse;
+  }
+
+  return base_code;
+}
+
+string CodeToString(ErrorCode code) {
+  // If the given code has both parts (i.e. the error code part and the flags
+  // part) then strip off the flags part since the switch statement below
+  // has case statements only for the base error code or a single flag but
+  // doesn't support any combinations of those.
+  if ((static_cast<int>(code) & static_cast<int>(ErrorCode::kSpecialFlags)) &&
+      (static_cast<int>(code) & ~static_cast<int>(ErrorCode::kSpecialFlags)))
+    code = static_cast<ErrorCode>(
+        static_cast<int>(code) & ~static_cast<int>(ErrorCode::kSpecialFlags));
+  switch (code) {
+    case ErrorCode::kSuccess: return "ErrorCode::kSuccess";
+    case ErrorCode::kError: return "ErrorCode::kError";
+    case ErrorCode::kOmahaRequestError: return "ErrorCode::kOmahaRequestError";
+    case ErrorCode::kOmahaResponseHandlerError:
+      return "ErrorCode::kOmahaResponseHandlerError";
+    case ErrorCode::kFilesystemCopierError:
+      return "ErrorCode::kFilesystemCopierError";
+    case ErrorCode::kPostinstallRunnerError:
+      return "ErrorCode::kPostinstallRunnerError";
+    case ErrorCode::kPayloadMismatchedType:
+      return "ErrorCode::kPayloadMismatchedType";
+    case ErrorCode::kInstallDeviceOpenError:
+      return "ErrorCode::kInstallDeviceOpenError";
+    case ErrorCode::kKernelDeviceOpenError:
+      return "ErrorCode::kKernelDeviceOpenError";
+    case ErrorCode::kDownloadTransferError:
+      return "ErrorCode::kDownloadTransferError";
+    case ErrorCode::kPayloadHashMismatchError:
+      return "ErrorCode::kPayloadHashMismatchError";
+    case ErrorCode::kPayloadSizeMismatchError:
+      return "ErrorCode::kPayloadSizeMismatchError";
+    case ErrorCode::kDownloadPayloadVerificationError:
+      return "ErrorCode::kDownloadPayloadVerificationError";
+    case ErrorCode::kDownloadNewPartitionInfoError:
+      return "ErrorCode::kDownloadNewPartitionInfoError";
+    case ErrorCode::kDownloadWriteError:
+      return "ErrorCode::kDownloadWriteError";
+    case ErrorCode::kNewRootfsVerificationError:
+      return "ErrorCode::kNewRootfsVerificationError";
+    case ErrorCode::kNewKernelVerificationError:
+      return "ErrorCode::kNewKernelVerificationError";
+    case ErrorCode::kSignedDeltaPayloadExpectedError:
+      return "ErrorCode::kSignedDeltaPayloadExpectedError";
+    case ErrorCode::kDownloadPayloadPubKeyVerificationError:
+      return "ErrorCode::kDownloadPayloadPubKeyVerificationError";
+    case ErrorCode::kPostinstallBootedFromFirmwareB:
+      return "ErrorCode::kPostinstallBootedFromFirmwareB";
+    case ErrorCode::kDownloadStateInitializationError:
+      return "ErrorCode::kDownloadStateInitializationError";
+    case ErrorCode::kDownloadInvalidMetadataMagicString:
+      return "ErrorCode::kDownloadInvalidMetadataMagicString";
+    case ErrorCode::kDownloadSignatureMissingInManifest:
+      return "ErrorCode::kDownloadSignatureMissingInManifest";
+    case ErrorCode::kDownloadManifestParseError:
+      return "ErrorCode::kDownloadManifestParseError";
+    case ErrorCode::kDownloadMetadataSignatureError:
+      return "ErrorCode::kDownloadMetadataSignatureError";
+    case ErrorCode::kDownloadMetadataSignatureVerificationError:
+      return "ErrorCode::kDownloadMetadataSignatureVerificationError";
+    case ErrorCode::kDownloadMetadataSignatureMismatch:
+      return "ErrorCode::kDownloadMetadataSignatureMismatch";
+    case ErrorCode::kDownloadOperationHashVerificationError:
+      return "ErrorCode::kDownloadOperationHashVerificationError";
+    case ErrorCode::kDownloadOperationExecutionError:
+      return "ErrorCode::kDownloadOperationExecutionError";
+    case ErrorCode::kDownloadOperationHashMismatch:
+      return "ErrorCode::kDownloadOperationHashMismatch";
+    case ErrorCode::kOmahaRequestEmptyResponseError:
+      return "ErrorCode::kOmahaRequestEmptyResponseError";
+    case ErrorCode::kOmahaRequestXMLParseError:
+      return "ErrorCode::kOmahaRequestXMLParseError";
+    case ErrorCode::kDownloadInvalidMetadataSize:
+      return "ErrorCode::kDownloadInvalidMetadataSize";
+    case ErrorCode::kDownloadInvalidMetadataSignature:
+      return "ErrorCode::kDownloadInvalidMetadataSignature";
+    case ErrorCode::kOmahaResponseInvalid:
+      return "ErrorCode::kOmahaResponseInvalid";
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+      return "ErrorCode::kOmahaUpdateIgnoredPerPolicy";
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+      return "ErrorCode::kOmahaUpdateDeferredPerPolicy";
+    case ErrorCode::kOmahaErrorInHTTPResponse:
+      return "ErrorCode::kOmahaErrorInHTTPResponse";
+    case ErrorCode::kDownloadOperationHashMissingError:
+      return "ErrorCode::kDownloadOperationHashMissingError";
+    case ErrorCode::kDownloadMetadataSignatureMissingError:
+      return "ErrorCode::kDownloadMetadataSignatureMissingError";
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+      return "ErrorCode::kOmahaUpdateDeferredForBackoff";
+    case ErrorCode::kPostinstallPowerwashError:
+      return "ErrorCode::kPostinstallPowerwashError";
+    case ErrorCode::kUpdateCanceledByChannelChange:
+      return "ErrorCode::kUpdateCanceledByChannelChange";
+    case ErrorCode::kUmaReportedMax:
+      return "ErrorCode::kUmaReportedMax";
+    case ErrorCode::kOmahaRequestHTTPResponseBase:
+      return "ErrorCode::kOmahaRequestHTTPResponseBase";
+    case ErrorCode::kResumedFlag:
+      return "Resumed";
+    case ErrorCode::kDevModeFlag:
+      return "DevMode";
+    case ErrorCode::kTestImageFlag:
+      return "TestImage";
+    case ErrorCode::kTestOmahaUrlFlag:
+      return "TestOmahaUrl";
+    case ErrorCode::kSpecialFlags:
+      return "ErrorCode::kSpecialFlags";
+    case ErrorCode::kPostinstallFirmwareRONotUpdatable:
+      return "ErrorCode::kPostinstallFirmwareRONotUpdatable";
+    case ErrorCode::kUnsupportedMajorPayloadVersion:
+      return "ErrorCode::kUnsupportedMajorPayloadVersion";
+    case ErrorCode::kUnsupportedMinorPayloadVersion:
+      return "ErrorCode::kUnsupportedMinorPayloadVersion";
+    case ErrorCode::kOmahaRequestXMLHasEntityDecl:
+      return "ErrorCode::kOmahaRequestXMLHasEntityDecl";
+    case ErrorCode::kFilesystemVerifierError:
+      return "ErrorCode::kFilesystemVerifierError";
+    // Don't add a default case to let the compiler warn about newly added
+    // error codes which should be added here.
+  }
+
+  return "Unknown error: " + base::UintToString(static_cast<unsigned>(code));
+}
+
+bool CreatePowerwashMarkerFile(const char* file_path) {
+  const char* marker_file = file_path ? file_path : kPowerwashMarkerFile;
+  bool result = utils::WriteFile(marker_file,
+                                 kPowerwashCommand,
+                                 strlen(kPowerwashCommand));
+  if (result) {
+    LOG(INFO) << "Created " << marker_file << " to powerwash on next reboot";
+  } else {
+    PLOG(ERROR) << "Error in creating powerwash marker file: " << marker_file;
+  }
+
+  return result;
+}
+
+bool DeletePowerwashMarkerFile(const char* file_path) {
+  const char* marker_file = file_path ? file_path : kPowerwashMarkerFile;
+  const base::FilePath kPowerwashMarkerPath(marker_file);
+  bool result = base::DeleteFile(kPowerwashMarkerPath, false);
+
+  if (result)
+    LOG(INFO) << "Successfully deleted the powerwash marker file : "
+              << marker_file;
+  else
+    PLOG(ERROR) << "Could not delete the powerwash marker file : "
+                << marker_file;
+
+  return result;
+}
+
+Time TimeFromStructTimespec(struct timespec *ts) {
+  int64_t us = static_cast<int64_t>(ts->tv_sec) * Time::kMicrosecondsPerSecond +
+      static_cast<int64_t>(ts->tv_nsec) / Time::kNanosecondsPerMicrosecond;
+  return Time::UnixEpoch() + TimeDelta::FromMicroseconds(us);
+}
+
+string StringVectorToString(const vector<string> &vec_str) {
+  string str = "[";
+  for (vector<string>::const_iterator i = vec_str.begin();
+       i != vec_str.end(); ++i) {
+    if (i != vec_str.begin())
+      str += ", ";
+    str += '"';
+    str += *i;
+    str += '"';
+  }
+  str += "]";
+  return str;
+}
+
+string CalculateP2PFileId(const string& payload_hash, size_t payload_size) {
+  string encoded_hash = brillo::data_encoding::Base64Encode(payload_hash);
+  return base::StringPrintf("cros_update_size_%" PRIuS "_hash_%s",
+                            payload_size,
+                            encoded_hash.c_str());
+}
+
+bool DecodeAndStoreBase64String(const string& base64_encoded,
+                                base::FilePath *out_path) {
+  brillo::Blob contents;
+
+  out_path->clear();
+
+  if (base64_encoded.size() == 0) {
+    LOG(ERROR) << "Can't decode empty string.";
+    return false;
+  }
+
+  if (!brillo::data_encoding::Base64Decode(base64_encoded, &contents) ||
+      contents.size() == 0) {
+    LOG(ERROR) << "Error decoding base64.";
+    return false;
+  }
+
+  FILE *file = base::CreateAndOpenTemporaryFile(out_path);
+  if (file == nullptr) {
+    LOG(ERROR) << "Error creating temporary file.";
+    return false;
+  }
+
+  if (fwrite(contents.data(), 1, contents.size(), file) != contents.size()) {
+    PLOG(ERROR) << "Error writing to temporary file.";
+    if (fclose(file) != 0)
+      PLOG(ERROR) << "Error closing temporary file.";
+    if (unlink(out_path->value().c_str()) != 0)
+      PLOG(ERROR) << "Error unlinking temporary file.";
+    out_path->clear();
+    return false;
+  }
+
+  if (fclose(file) != 0) {
+    PLOG(ERROR) << "Error closing temporary file.";
+    out_path->clear();
+    return false;
+  }
+
+  return true;
+}
+
+bool ConvertToOmahaInstallDate(Time time, int *out_num_days) {
+  time_t unix_time = time.ToTimeT();
+  // Output of: date +"%s" --date="Jan 1, 2007 0:00 PST".
+  const time_t kOmahaEpoch = 1167638400;
+  const int64_t kNumSecondsPerWeek = 7*24*3600;
+  const int64_t kNumDaysPerWeek = 7;
+
+  time_t omaha_time = unix_time - kOmahaEpoch;
+
+  if (omaha_time < 0)
+    return false;
+
+  // Note, as per the comment in utils.h we are deliberately not
+  // handling DST correctly.
+
+  int64_t num_weeks_since_omaha_epoch = omaha_time / kNumSecondsPerWeek;
+  *out_num_days = num_weeks_since_omaha_epoch * kNumDaysPerWeek;
+
+  return true;
+}
+
+bool GetMinorVersion(const brillo::KeyValueStore& store,
+                     uint32_t* minor_version) {
+  string result;
+  if (store.GetString("PAYLOAD_MINOR_VERSION", &result)) {
+    if (!base::StringToUint(result, minor_version)) {
+      LOG(ERROR) << "StringToUint failed when parsing delta minor version.";
+      return false;
+    }
+    return true;
+  }
+  return false;
+}
+
+bool ReadExtents(const string& path, const vector<Extent>& extents,
+                 brillo::Blob* out_data, ssize_t out_data_size,
+                 size_t block_size) {
+  brillo::Blob data(out_data_size);
+  ssize_t bytes_read = 0;
+  int fd = open(path.c_str(), O_RDONLY);
+  TEST_AND_RETURN_FALSE_ERRNO(fd >= 0);
+  ScopedFdCloser fd_closer(&fd);
+
+  for (const Extent& extent : extents) {
+    ssize_t bytes_read_this_iteration = 0;
+    ssize_t bytes = extent.num_blocks() * block_size;
+    TEST_AND_RETURN_FALSE(bytes_read + bytes <= out_data_size);
+    TEST_AND_RETURN_FALSE(utils::PReadAll(fd,
+                                          &data[bytes_read],
+                                          bytes,
+                                          extent.start_block() * block_size,
+                                          &bytes_read_this_iteration));
+    TEST_AND_RETURN_FALSE(bytes_read_this_iteration == bytes);
+    bytes_read += bytes_read_this_iteration;
+  }
+  TEST_AND_RETURN_FALSE(out_data_size == bytes_read);
+  *out_data = data;
+  return true;
+}
+
+bool GetBootId(string* boot_id) {
+  TEST_AND_RETURN_FALSE(
+      base::ReadFileToString(base::FilePath(kBootIdPath), boot_id));
+  base::TrimWhitespaceASCII(*boot_id, base::TRIM_TRAILING, boot_id);
+  return true;
+}
+
+}  // namespace utils
+
+}  // namespace chromeos_update_engine
diff --git a/common/utils.h b/common/utils.h
new file mode 100644
index 0000000..0440dd8
--- /dev/null
+++ b/common/utils.h
@@ -0,0 +1,510 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_COMMON_UTILS_H_
+#define UPDATE_ENGINE_COMMON_UTILS_H_
+
+#include <errno.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <map>
+#include <memory>
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/posix/eintr_wrapper.h>
+#include <base/time/time.h>
+#include <brillo/key_value_store.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/action_processor.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/payload_consumer/file_descriptor.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+namespace utils {
+
+// Converts a struct timespec representing a number of seconds since
+// the Unix epoch to a base::Time. Sub-microsecond time is rounded
+// down.
+base::Time TimeFromStructTimespec(struct timespec *ts);
+
+// Formats |vec_str| as a string of the form ["<elem1>", "<elem2>"].
+// Does no escaping, only use this for presentation in error messages.
+std::string StringVectorToString(const std::vector<std::string> &vec_str);
+
+// Calculates the p2p file id from payload hash and size
+std::string CalculateP2PFileId(const std::string& payload_hash,
+                               size_t payload_size);
+
+// Parse the firmware version from one line of output from the
+// "mosys" command.
+std::string ParseECVersion(std::string input_line);
+
+// Writes the data passed to path. The file at path will be overwritten if it
+// exists. Returns true on success, false otherwise.
+bool WriteFile(const char* path, const void* data, int data_len);
+
+// Calls write() or pwrite() repeatedly until all count bytes at buf are
+// written to fd or an error occurs. Returns true on success.
+bool WriteAll(int fd, const void* buf, size_t count);
+bool PWriteAll(int fd, const void* buf, size_t count, off_t offset);
+
+bool WriteAll(FileDescriptorPtr fd, const void* buf, size_t count);
+bool PWriteAll(FileDescriptorPtr fd,
+               const void* buf,
+               size_t count,
+               off_t offset);
+
+// Calls pread() repeatedly until count bytes are read, or EOF is reached.
+// Returns number of bytes read in *bytes_read. Returns true on success.
+bool PReadAll(int fd, void* buf, size_t count, off_t offset,
+              ssize_t* out_bytes_read);
+
+bool PReadAll(FileDescriptorPtr fd, void* buf, size_t count, off_t offset,
+              ssize_t* out_bytes_read);
+
+// Opens |path| for reading and appends its entire content to the container
+// pointed to by |out_p|. Returns true upon successfully reading all of the
+// file's content, false otherwise, in which case the state of the output
+// container is unknown. ReadFileChunk starts reading the file from |offset|; if
+// |size| is not -1, only up to |size| bytes are read in.
+bool ReadFile(const std::string& path, brillo::Blob* out_p);
+bool ReadFile(const std::string& path, std::string* out_p);
+bool ReadFileChunk(const std::string& path, off_t offset, off_t size,
+                   brillo::Blob* out_p);
+
+// Invokes |cmd| in a pipe and appends its stdout to the container pointed to by
+// |out_p|. Returns true upon successfully reading all of the output, false
+// otherwise, in which case the state of the output container is unknown.
+bool ReadPipe(const std::string& cmd, std::string* out_p);
+
+// Returns the size of the block device at the file descriptor fd. If an error
+// occurs, -1 is returned.
+off_t BlockDevSize(int fd);
+
+// Returns the size of the file at path, or the file desciptor fd. If the file
+// is actually a block device, this function will automatically call
+// BlockDevSize. If the file doesn't exist or some error occurrs, -1 is
+// returned.
+off_t FileSize(const std::string& path);
+off_t FileSize(int fd);
+
+std::string ErrnoNumberAsString(int err);
+
+// Returns true if the file exists for sure. Returns false if it doesn't exist,
+// or an error occurs.
+bool FileExists(const char* path);
+
+// Returns true if |path| exists and is a symbolic link.
+bool IsSymlink(const char* path);
+
+// Try attaching UBI |volume_num|. If there is any error executing required
+// commands to attach the volume, this function returns false. This function
+// only returns true if "/dev/ubi%d_0" becomes available in |timeout| seconds.
+bool TryAttachingUbiVolume(int volume_num, int timeout);
+
+// If |base_filename_template| is neither absolute (starts with "/") nor
+// explicitly relative to the current working directory (starts with "./" or
+// "../"), then it is prepended the system's temporary directory. On success,
+// stores the name of the new temporary file in |filename|. If |fd| is
+// non-null, the file descriptor returned by mkstemp is written to it and
+// kept open; otherwise, it is closed. The template must end with "XXXXXX".
+// Returns true on success.
+bool MakeTempFile(const std::string& base_filename_template,
+                  std::string* filename,
+                  int* fd);
+
+// If |base_dirname_template| is neither absolute (starts with "/") nor
+// explicitly relative to the current working directory (starts with "./" or
+// "../"), then it is prepended the system's temporary directory. On success,
+// stores the name of the new temporary directory in |dirname|. The template
+// must end with "XXXXXX". Returns true on success.
+bool MakeTempDirectory(const std::string& base_dirname_template,
+                       std::string* dirname);
+
+// Splits the partition device name into the block device name and partition
+// number. For example, "/dev/sda3" will be split into {"/dev/sda", 3} and
+// "/dev/mmcblk0p2" into {"/dev/mmcblk0", 2}
+// Returns false when malformed device name is passed in.
+// If both output parameters are omitted (null), can be used
+// just to test the validity of the device name. Note that the function
+// simply checks if the device name looks like a valid device, no other
+// checks are performed (i.e. it doesn't check if the device actually exists).
+bool SplitPartitionName(const std::string& partition_name,
+                        std::string* out_disk_name,
+                        int* out_partition_num);
+
+// Builds a partition device name from the block device name and partition
+// number. For example:
+// {"/dev/sda", 1} => "/dev/sda1"
+// {"/dev/mmcblk2", 12} => "/dev/mmcblk2p12"
+// Returns empty string when invalid parameters are passed in
+std::string MakePartitionName(const std::string& disk_name,
+                              int partition_num);
+
+// Similar to "MakePartitionName" but returns a name that is suitable for
+// mounting. On NAND system we can write to "/dev/ubiX_0", which is what
+// MakePartitionName returns, but we cannot mount that device. To mount, we
+// have to use "/dev/ubiblockX_0" for rootfs. Stateful and OEM partitions are
+// mountable with "/dev/ubiX_0". The input is a partition device such as
+// /dev/sda3. Return empty string on error.
+std::string MakePartitionNameForMount(const std::string& part_name);
+
+// Synchronously mount or unmount a filesystem. Return true on success.
+// When mounting, it will attempt to mount the the device as "ext3", "ext2" and
+// "squashfs", with the passed |flags| options.
+bool MountFilesystem(const std::string& device, const std::string& mountpoint,
+                     unsigned long flags);  // NOLINT(runtime/int)
+bool UnmountFilesystem(const std::string& mountpoint);
+
+// Returns the block count and the block byte size of the file system on
+// |device| (which may be a real device or a path to a filesystem image) or on
+// an opened file descriptor |fd|. The actual file-system size is |block_count|
+// * |block_size| bytes. Returns true on success, false otherwise.
+bool GetFilesystemSize(const std::string& device,
+                       int* out_block_count,
+                       int* out_block_size);
+bool GetFilesystemSizeFromFD(int fd,
+                             int* out_block_count,
+                             int* out_block_size);
+
+// Determines the block count and block size of the ext3 fs. At least 2048 bytes
+// are required to parse the first superblock. Returns whether the buffer
+// contains a valid ext3 filesystem and the values were parsed.
+bool GetExt3Size(const uint8_t* buffer, size_t buffer_size,
+                 int* out_block_count,
+                 int* out_block_size);
+
+// Determines the block count and block size of the squashfs v4 fs. At least 96
+// bytes are required to parse the header of the filesystem. Since squashfs
+// doesn't define a physical block size, a value of 4096 is used for the block
+// size, which is the default padding when creating the filesystem.
+// Returns whether the buffer contains a valid squashfs v4 header and the size
+// was parsed. Only little endian squashfs is supported.
+bool GetSquashfs4Size(const uint8_t* buffer, size_t buffer_size,
+                      int* out_block_count,
+                      int* out_block_size);
+
+// Returns whether the filesystem is an ext[234] filesystem. In case of failure,
+// such as if the file |device| doesn't exists or can't be read, it returns
+// false.
+bool IsExtFilesystem(const std::string& device);
+
+// Returns whether the filesystem is a squashfs filesystem. In case of failure,
+// such as if the file |device| doesn't exists or can't be read, it returns
+// false.
+bool IsSquashfsFilesystem(const std::string& device);
+
+// Returns a human-readable string with the file format based on magic constants
+// on the header of the file.
+std::string GetFileFormat(const std::string& path);
+
+// Returns the string representation of the given UTC time.
+// such as "11/14/2011 14:05:30 GMT".
+std::string ToString(const base::Time utc_time);
+
+// Returns true or false depending on the value of b.
+std::string ToString(bool b);
+
+// Returns a string representation of the given enum.
+std::string ToString(DownloadSource source);
+
+// Returns a string representation of the given enum.
+std::string ToString(PayloadType payload_type);
+
+// Schedules a Main Loop callback to trigger the crash reporter to perform an
+// upload as if this process had crashed.
+void ScheduleCrashReporterUpload();
+
+// Fuzzes an integer |value| randomly in the range:
+// [value - range / 2, value + range - range / 2]
+int FuzzInt(int value, unsigned int range);
+
+// Log a string in hex to LOG(INFO). Useful for debugging.
+void HexDumpArray(const uint8_t* const arr, const size_t length);
+inline void HexDumpString(const std::string& str) {
+  HexDumpArray(reinterpret_cast<const uint8_t*>(str.data()), str.size());
+}
+inline void HexDumpVector(const brillo::Blob& vect) {
+  HexDumpArray(vect.data(), vect.size());
+}
+
+template<typename KeyType, typename ValueType>
+bool MapContainsKey(const std::map<KeyType, ValueType>& m, const KeyType& k) {
+  return m.find(k) != m.end();
+}
+template<typename KeyType>
+bool SetContainsKey(const std::set<KeyType>& s, const KeyType& k) {
+  return s.find(k) != s.end();
+}
+
+template<typename T>
+bool VectorContainsValue(const std::vector<T>& vect, const T& value) {
+  return std::find(vect.begin(), vect.end(), value) != vect.end();
+}
+
+template<typename T>
+bool VectorIndexOf(const std::vector<T>& vect, const T& value,
+                   typename std::vector<T>::size_type* out_index) {
+  typename std::vector<T>::const_iterator it = std::find(vect.begin(),
+                                                         vect.end(),
+                                                         value);
+  if (it == vect.end()) {
+    return false;
+  } else {
+    *out_index = it - vect.begin();
+    return true;
+  }
+}
+
+// Cgroups cpu shares constants. 1024 is the default shares a standard process
+// gets and 2 is the minimum value. We set High as a value that gives the
+// update-engine 2x the cpu share of a standard process.
+enum CpuShares {
+  kCpuSharesHigh = 2048,
+  kCpuSharesNormal = 1024,
+  kCpuSharesLow = 2,
+};
+
+// Sets the current process shares to |shares|. Returns true on
+// success, false otherwise.
+bool SetCpuShares(CpuShares shares);
+
+// Converts seconds into human readable notation including days, hours, minutes
+// and seconds. For example, 185 will yield 3m5s, 4300 will yield 1h11m40s, and
+// 360000 will yield 4d4h0m0s.  Zero padding not applied. Seconds are always
+// shown in the result.
+std::string FormatSecs(unsigned secs);
+
+// Converts a TimeDelta into human readable notation including days, hours,
+// minutes, seconds and fractions of a second down to microsecond granularity,
+// as necessary; for example, an output of 5d2h0m15.053s means that the input
+// time was precise to the milliseconds only. Zero padding not applied, except
+// for fractions. Seconds are always shown, but fractions thereof are only shown
+// when applicable. If |delta| is negative, the output will have a leading '-'
+// followed by the absolute duration.
+std::string FormatTimeDelta(base::TimeDelta delta);
+
+// This method transforms the given error code to be suitable for UMA and
+// for error classification purposes by removing the higher order bits and
+// aggregating error codes beyond the enum range, etc. This method is
+// idempotent, i.e. if called with a value previously returned by this method,
+// it'll return the same value again.
+ErrorCode GetBaseErrorCode(ErrorCode code);
+
+// Returns a string representation of the ErrorCodes (either the base
+// error codes or the bit flags) for logging purposes.
+std::string CodeToString(ErrorCode code);
+
+// Creates the powerwash marker file with the appropriate commands in it.  Uses
+// |file_path| as the path to the marker file if non-null, otherwise uses the
+// global default. Returns true if successfully created.  False otherwise.
+bool CreatePowerwashMarkerFile(const char* file_path);
+
+// Deletes the marker file used to trigger Powerwash using clobber-state.  Uses
+// |file_path| as the path to the marker file if non-null, otherwise uses the
+// global default. Returns true if successfully deleted. False otherwise.
+bool DeletePowerwashMarkerFile(const char* file_path);
+
+// Decodes the data in |base64_encoded| and stores it in a temporary
+// file. Returns false if the given data is empty, not well-formed
+// base64 or if an error occurred. If true is returned, the decoded
+// data is stored in the file returned in |out_path|. The file should
+// be deleted when no longer needed.
+bool DecodeAndStoreBase64String(const std::string& base64_encoded,
+                                base::FilePath *out_path);
+
+// Converts |time| to an Omaha InstallDate which is defined as "the
+// number of PST8PDT calendar weeks since Jan 1st 2007 0:00 PST, times
+// seven" with PST8PDT defined as "Pacific Time" (e.g. UTC-07:00 if
+// daylight savings is observed and UTC-08:00 otherwise.)
+//
+// If the passed in |time| variable is before Monday January 1st 2007
+// 0:00 PST, False is returned and the value returned in
+// |out_num_days| is undefined. Otherwise the number of PST8PDT
+// calendar weeks since that date times seven is returned in
+// |out_num_days| and the function returns True.
+//
+// (NOTE: This function does not currently take daylight savings time
+// into account so the result may up to one hour off. This is because
+// the glibc date and timezone routines depend on the TZ environment
+// variable and changing environment variables is not thread-safe.
+bool ConvertToOmahaInstallDate(base::Time time, int *out_num_days);
+
+// Look for the minor version value in the passed |store| and set
+// |minor_version| to that value. Return whether the value was found and valid.
+bool GetMinorVersion(const brillo::KeyValueStore& store,
+                     uint32_t* minor_version);
+
+// This function reads the specified data in |extents| into |out_data|. The
+// extents are read from the file at |path|. |out_data_size| is the size of
+// |out_data|. Returns false if the number of bytes to read given in
+// |extents| does not equal |out_data_size|.
+bool ReadExtents(const std::string& path, const std::vector<Extent>& extents,
+                 brillo::Blob* out_data, ssize_t out_data_size,
+                 size_t block_size);
+
+// Read the current boot identifier and store it in |boot_id|. This identifier
+// is constants during the same boot of the kernel and is regenerated after
+// reboot. Returns whether it succeeded getting the boot_id.
+bool GetBootId(std::string* boot_id);
+
+}  // namespace utils
+
+
+// Utility class to close a file descriptor
+class ScopedFdCloser {
+ public:
+  explicit ScopedFdCloser(int* fd) : fd_(fd) {}
+  ~ScopedFdCloser() {
+    if (should_close_ && fd_ && (*fd_ >= 0) && !IGNORE_EINTR(close(*fd_)))
+      *fd_ = -1;
+  }
+  void set_should_close(bool should_close) { should_close_ = should_close; }
+ private:
+  int* fd_;
+  bool should_close_ = true;
+  DISALLOW_COPY_AND_ASSIGN(ScopedFdCloser);
+};
+
+// Utility class to delete a file when it goes out of scope.
+class ScopedPathUnlinker {
+ public:
+  explicit ScopedPathUnlinker(const std::string& path)
+      : path_(path),
+        should_remove_(true) {}
+  ~ScopedPathUnlinker() {
+    if (should_remove_ && unlink(path_.c_str()) < 0) {
+      PLOG(ERROR) << "Unable to unlink path " << path_;
+    }
+  }
+  void set_should_remove(bool should_remove) { should_remove_ = should_remove; }
+
+ private:
+  const std::string path_;
+  bool should_remove_;
+  DISALLOW_COPY_AND_ASSIGN(ScopedPathUnlinker);
+};
+
+// Utility class to delete an empty directory when it goes out of scope.
+class ScopedDirRemover {
+ public:
+  explicit ScopedDirRemover(const std::string& path)
+      : path_(path),
+        should_remove_(true) {}
+  ~ScopedDirRemover() {
+    if (should_remove_ && (rmdir(path_.c_str()) < 0)) {
+      PLOG(ERROR) << "Unable to remove dir " << path_;
+    }
+  }
+  void set_should_remove(bool should_remove) { should_remove_ = should_remove; }
+
+ protected:
+  const std::string path_;
+
+ private:
+  bool should_remove_;
+  DISALLOW_COPY_AND_ASSIGN(ScopedDirRemover);
+};
+
+// A little object to call ActionComplete on the ActionProcessor when
+// it's destructed.
+class ScopedActionCompleter {
+ public:
+  explicit ScopedActionCompleter(ActionProcessor* processor,
+                                 AbstractAction* action)
+      : processor_(processor),
+        action_(action),
+        code_(ErrorCode::kError),
+        should_complete_(true) {}
+  ~ScopedActionCompleter() {
+    if (should_complete_)
+      processor_->ActionComplete(action_, code_);
+  }
+  void set_code(ErrorCode code) { code_ = code; }
+  void set_should_complete(bool should_complete) {
+    should_complete_ = should_complete;
+  }
+  ErrorCode get_code() const { return code_; }
+
+ private:
+  ActionProcessor* processor_;
+  AbstractAction* action_;
+  ErrorCode code_;
+  bool should_complete_;
+  DISALLOW_COPY_AND_ASSIGN(ScopedActionCompleter);
+};
+
+}  // namespace chromeos_update_engine
+
+#define TEST_AND_RETURN_FALSE_ERRNO(_x)                                        \
+  do {                                                                         \
+    bool _success = static_cast<bool>(_x);                                     \
+    if (!_success) {                                                           \
+      std::string _msg =                                                       \
+          chromeos_update_engine::utils::ErrnoNumberAsString(errno);           \
+      LOG(ERROR) << #_x " failed: " << _msg;                                   \
+      return false;                                                            \
+    }                                                                          \
+  } while (0)
+
+#define TEST_AND_RETURN_FALSE(_x)                                              \
+  do {                                                                         \
+    bool _success = static_cast<bool>(_x);                                     \
+    if (!_success) {                                                           \
+      LOG(ERROR) << #_x " failed.";                                            \
+      return false;                                                            \
+    }                                                                          \
+  } while (0)
+
+#define TEST_AND_RETURN_ERRNO(_x)                                              \
+  do {                                                                         \
+    bool _success = static_cast<bool>(_x);                                     \
+    if (!_success) {                                                           \
+      std::string _msg =                                                       \
+          chromeos_update_engine::utils::ErrnoNumberAsString(errno);           \
+      LOG(ERROR) << #_x " failed: " << _msg;                                   \
+      return;                                                                  \
+    }                                                                          \
+  } while (0)
+
+#define TEST_AND_RETURN(_x)                                                    \
+  do {                                                                         \
+    bool _success = static_cast<bool>(_x);                                     \
+    if (!_success) {                                                           \
+      LOG(ERROR) << #_x " failed.";                                            \
+      return;                                                                  \
+    }                                                                          \
+  } while (0)
+
+#define TEST_AND_RETURN_FALSE_ERRCODE(_x)                                      \
+  do {                                                                         \
+    errcode_t _error = (_x);                                                   \
+    if (_error) {                                                              \
+      errno = _error;                                                          \
+      LOG(ERROR) << #_x " failed: " << _error;                                 \
+      return false;                                                            \
+    }                                                                          \
+  } while (0)
+
+#endif  // UPDATE_ENGINE_COMMON_UTILS_H_
diff --git a/common/utils_unittest.cc b/common/utils_unittest.cc
new file mode 100644
index 0000000..02f919e
--- /dev/null
+++ b/common/utils_unittest.cc
@@ -0,0 +1,569 @@
+//
+// Copyright (C) 2012 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 "update_engine/common/utils.h"
+
+#include <errno.h>
+#include <stdint.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/files/scoped_temp_dir.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+
+using brillo::FakeMessageLoop;
+using std::map;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class UtilsTest : public ::testing::Test { };
+
+TEST(UtilsTest, CanParseECVersion) {
+  // Should be able to parse and valid key value line.
+  EXPECT_EQ("12345", utils::ParseECVersion("fw_version=12345"));
+  EXPECT_EQ("123456", utils::ParseECVersion(
+      "b=1231a fw_version=123456 a=fasd2"));
+  EXPECT_EQ("12345", utils::ParseECVersion("fw_version=12345"));
+  EXPECT_EQ("00VFA616", utils::ParseECVersion(
+      "vendor=\"sam\" fw_version=\"00VFA616\""));
+
+  // For invalid entries, should return the empty string.
+  EXPECT_EQ("", utils::ParseECVersion("b=1231a fw_version a=fasd2"));
+}
+
+TEST(UtilsTest, ReadFileFailure) {
+  brillo::Blob empty;
+  EXPECT_FALSE(utils::ReadFile("/this/doesn't/exist", &empty));
+}
+
+TEST(UtilsTest, ReadFileChunk) {
+  base::FilePath file;
+  EXPECT_TRUE(base::CreateTemporaryFile(&file));
+  ScopedPathUnlinker unlinker(file.value());
+  brillo::Blob data;
+  const size_t kSize = 1024 * 1024;
+  for (size_t i = 0; i < kSize; i++) {
+    data.push_back(i % 255);
+  }
+  EXPECT_TRUE(utils::WriteFile(file.value().c_str(), data.data(), data.size()));
+  brillo::Blob in_data;
+  EXPECT_TRUE(utils::ReadFileChunk(file.value().c_str(), kSize, 10, &in_data));
+  EXPECT_TRUE(in_data.empty());
+  EXPECT_TRUE(utils::ReadFileChunk(file.value().c_str(), 0, -1, &in_data));
+  EXPECT_TRUE(data == in_data);
+  in_data.clear();
+  EXPECT_TRUE(utils::ReadFileChunk(file.value().c_str(), 10, 20, &in_data));
+  EXPECT_TRUE(brillo::Blob(data.begin() + 10, data.begin() + 10 + 20) ==
+              in_data);
+}
+
+TEST(UtilsTest, ErrnoNumberAsStringTest) {
+  EXPECT_EQ("No such file or directory", utils::ErrnoNumberAsString(ENOENT));
+}
+
+TEST(UtilsTest, IsSymlinkTest) {
+  string temp_dir;
+  EXPECT_TRUE(utils::MakeTempDirectory("symlink-test.XXXXXX", &temp_dir));
+  string temp_file = temp_dir + "/temp-file";
+  EXPECT_TRUE(utils::WriteFile(temp_file.c_str(), "", 0));
+  string temp_symlink = temp_dir + "/temp-symlink";
+  EXPECT_EQ(0, symlink(temp_file.c_str(), temp_symlink.c_str()));
+  EXPECT_FALSE(utils::IsSymlink(temp_dir.c_str()));
+  EXPECT_FALSE(utils::IsSymlink(temp_file.c_str()));
+  EXPECT_TRUE(utils::IsSymlink(temp_symlink.c_str()));
+  EXPECT_FALSE(utils::IsSymlink("/non/existent/path"));
+  EXPECT_TRUE(base::DeleteFile(base::FilePath(temp_dir), true));
+}
+
+TEST(UtilsTest, SplitPartitionNameTest) {
+  string disk;
+  int part_num;
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/sda3", &disk, &part_num));
+  EXPECT_EQ("/dev/sda", disk);
+  EXPECT_EQ(3, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/sdp1234", &disk, &part_num));
+  EXPECT_EQ("/dev/sdp", disk);
+  EXPECT_EQ(1234, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/mmcblk0p3", &disk, &part_num));
+  EXPECT_EQ("/dev/mmcblk0", disk);
+  EXPECT_EQ(3, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/ubiblock3_2", &disk, &part_num));
+  EXPECT_EQ("/dev/ubiblock", disk);
+  EXPECT_EQ(3, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/loop10", &disk, &part_num));
+  EXPECT_EQ("/dev/loop", disk);
+  EXPECT_EQ(10, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/loop28p11", &disk, &part_num));
+  EXPECT_EQ("/dev/loop28", disk);
+  EXPECT_EQ(11, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/loop10_0", &disk, &part_num));
+  EXPECT_EQ("/dev/loop", disk);
+  EXPECT_EQ(10, part_num);
+
+  EXPECT_TRUE(utils::SplitPartitionName("/dev/loop28p11_0", &disk, &part_num));
+  EXPECT_EQ("/dev/loop28", disk);
+  EXPECT_EQ(11, part_num);
+
+  EXPECT_FALSE(utils::SplitPartitionName("/dev/mmcblk0p", &disk, &part_num));
+  EXPECT_FALSE(utils::SplitPartitionName("/dev/sda", &disk, &part_num));
+  EXPECT_FALSE(utils::SplitPartitionName("/dev/foo/bar", &disk, &part_num));
+  EXPECT_FALSE(utils::SplitPartitionName("/", &disk, &part_num));
+  EXPECT_FALSE(utils::SplitPartitionName("", &disk, &part_num));
+}
+
+TEST(UtilsTest, MakePartitionNameTest) {
+  EXPECT_EQ("/dev/sda4", utils::MakePartitionName("/dev/sda", 4));
+  EXPECT_EQ("/dev/sda123", utils::MakePartitionName("/dev/sda", 123));
+  EXPECT_EQ("/dev/mmcblk2", utils::MakePartitionName("/dev/mmcblk", 2));
+  EXPECT_EQ("/dev/mmcblk0p2", utils::MakePartitionName("/dev/mmcblk0", 2));
+  EXPECT_EQ("/dev/loop8", utils::MakePartitionName("/dev/loop", 8));
+  EXPECT_EQ("/dev/loop12p2", utils::MakePartitionName("/dev/loop12", 2));
+  EXPECT_EQ("/dev/ubi5_0", utils::MakePartitionName("/dev/ubiblock", 5));
+  EXPECT_EQ("/dev/mtd4", utils::MakePartitionName("/dev/ubiblock", 4));
+  EXPECT_EQ("/dev/ubi3_0", utils::MakePartitionName("/dev/ubiblock", 3));
+  EXPECT_EQ("/dev/mtd2", utils::MakePartitionName("/dev/ubiblock", 2));
+  EXPECT_EQ("/dev/ubi1_0", utils::MakePartitionName("/dev/ubiblock", 1));
+}
+
+TEST(UtilsTest, MakePartitionNameForMountTest) {
+  EXPECT_EQ("/dev/sda4", utils::MakePartitionNameForMount("/dev/sda4"));
+  EXPECT_EQ("/dev/sda123", utils::MakePartitionNameForMount("/dev/sda123"));
+  EXPECT_EQ("/dev/mmcblk2", utils::MakePartitionNameForMount("/dev/mmcblk2"));
+  EXPECT_EQ("/dev/mmcblk0p2",
+            utils::MakePartitionNameForMount("/dev/mmcblk0p2"));
+  EXPECT_EQ("/dev/loop0", utils::MakePartitionNameForMount("/dev/loop0"));
+  EXPECT_EQ("/dev/loop8", utils::MakePartitionNameForMount("/dev/loop8"));
+  EXPECT_EQ("/dev/loop12p2",
+            utils::MakePartitionNameForMount("/dev/loop12p2"));
+  EXPECT_EQ("/dev/ubiblock5_0",
+            utils::MakePartitionNameForMount("/dev/ubiblock5_0"));
+  EXPECT_EQ("/dev/mtd4",
+            utils::MakePartitionNameForMount("/dev/ubi4_0"));
+  EXPECT_EQ("/dev/ubiblock3_0",
+            utils::MakePartitionNameForMount("/dev/ubiblock3"));
+  EXPECT_EQ("/dev/mtd2", utils::MakePartitionNameForMount("/dev/ubi2"));
+  EXPECT_EQ("/dev/ubi1_0",
+            utils::MakePartitionNameForMount("/dev/ubiblock1"));
+}
+
+namespace {
+// Compares cpu shares and returns an integer that is less
+// than, equal to or greater than 0 if |shares_lhs| is,
+// respectively, lower than, same as or higher than |shares_rhs|.
+int CompareCpuShares(utils::CpuShares shares_lhs,
+                     utils::CpuShares shares_rhs) {
+  return static_cast<int>(shares_lhs) - static_cast<int>(shares_rhs);
+}
+}  // namespace
+
+// Tests the CPU shares enum is in the order we expect it.
+TEST(UtilsTest, CompareCpuSharesTest) {
+  EXPECT_LT(CompareCpuShares(utils::kCpuSharesLow,
+                             utils::kCpuSharesNormal), 0);
+  EXPECT_GT(CompareCpuShares(utils::kCpuSharesNormal,
+                             utils::kCpuSharesLow), 0);
+  EXPECT_EQ(CompareCpuShares(utils::kCpuSharesNormal,
+                             utils::kCpuSharesNormal), 0);
+  EXPECT_GT(CompareCpuShares(utils::kCpuSharesHigh,
+                             utils::kCpuSharesNormal), 0);
+}
+
+TEST(UtilsTest, FuzzIntTest) {
+  static const unsigned int kRanges[] = { 0, 1, 2, 20 };
+  for (unsigned int range : kRanges) {
+    const int kValue = 50;
+    for (int tries = 0; tries < 100; ++tries) {
+      int value = utils::FuzzInt(kValue, range);
+      EXPECT_GE(value, kValue - range / 2);
+      EXPECT_LE(value, kValue + range - range / 2);
+    }
+  }
+}
+
+TEST(UtilsTest, RunAsRootGetFilesystemSizeTest) {
+  string img;
+  EXPECT_TRUE(utils::MakeTempFile("img.XXXXXX", &img, nullptr));
+  ScopedPathUnlinker img_unlinker(img);
+  test_utils::CreateExtImageAtPath(img, nullptr);
+  // Extend the "partition" holding the file system from 10MiB to 20MiB.
+  EXPECT_EQ(0, test_utils::System(base::StringPrintf(
+      "dd if=/dev/zero of=%s seek=20971519 bs=1 count=1 status=none",
+      img.c_str())));
+  EXPECT_EQ(20 * 1024 * 1024, utils::FileSize(img));
+  int block_count = 0;
+  int block_size = 0;
+  EXPECT_TRUE(utils::GetFilesystemSize(img, &block_count, &block_size));
+  EXPECT_EQ(4096, block_size);
+  EXPECT_EQ(10 * 1024 * 1024 / 4096, block_count);
+}
+
+// Squashfs example filesystem, generated with:
+//   echo hola>hola
+//   mksquashfs hola hola.sqfs -noappend -nopad
+//   hexdump hola.sqfs -e '16/1 "%02x, " "\n"'
+const uint8_t kSquashfsFile[] = {
+  0x68, 0x73, 0x71, 0x73, 0x02, 0x00, 0x00, 0x00,  // magic, inodes
+  0x3e, 0x49, 0x61, 0x54, 0x00, 0x00, 0x02, 0x00,
+  0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x11, 0x00,
+  0xc0, 0x00, 0x02, 0x00, 0x04, 0x00, 0x00, 0x00,  // flags, noids, major, minor
+  0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,  // root_inode
+  0xef, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,  // bytes_used
+  0xe7, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+  0x93, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+  0xbd, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+  0xd5, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+  0x68, 0x6f, 0x6c, 0x61, 0x0a, 0x2c, 0x00, 0x78,
+  0xda, 0x63, 0x62, 0x58, 0xc2, 0xc8, 0xc0, 0xc0,
+  0xc8, 0xd0, 0x6b, 0x91, 0x18, 0x02, 0x64, 0xa0,
+  0x00, 0x56, 0x06, 0x90, 0xcc, 0x7f, 0xb0, 0xbc,
+  0x9d, 0x67, 0x62, 0x08, 0x13, 0x54, 0x1c, 0x44,
+  0x4b, 0x03, 0x31, 0x33, 0x10, 0x03, 0x00, 0xb5,
+  0x87, 0x04, 0x89, 0x16, 0x00, 0x78, 0xda, 0x63,
+  0x60, 0x80, 0x00, 0x46, 0x28, 0xcd, 0xc4, 0xc0,
+  0xcc, 0x90, 0x91, 0x9f, 0x93, 0x08, 0x00, 0x04,
+  0x70, 0x01, 0xab, 0x10, 0x80, 0x60, 0x00, 0x00,
+  0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00,
+  0x01, 0x00, 0x00, 0x00, 0x00, 0xab, 0x00, 0x00,
+  0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x78,
+  0xda, 0x63, 0x60, 0x80, 0x00, 0x05, 0x28, 0x0d,
+  0x00, 0x01, 0x10, 0x00, 0x21, 0xc5, 0x00, 0x00,
+  0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x80, 0x99,
+  0xcd, 0x02, 0x00, 0x88, 0x13, 0x00, 0x00, 0xdd,
+  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+TEST(UtilsTest, GetSquashfs4Size) {
+  uint8_t buffer[sizeof(kSquashfsFile)];
+  memcpy(buffer, kSquashfsFile, sizeof(kSquashfsFile));
+
+  int block_count = -1;
+  int block_size = -1;
+  // Not enough bytes passed.
+  EXPECT_FALSE(utils::GetSquashfs4Size(buffer, 10, nullptr, nullptr));
+
+  // The whole file system is passed, which is enough for parsing.
+  EXPECT_TRUE(utils::GetSquashfs4Size(buffer, sizeof(kSquashfsFile),
+                                      &block_count, &block_size));
+  EXPECT_EQ(4096, block_size);
+  EXPECT_EQ(1, block_count);
+
+  // Modify the major version to 5.
+  uint16_t* s_major = reinterpret_cast<uint16_t*>(buffer + 0x1c);
+  *s_major = 5;
+  EXPECT_FALSE(utils::GetSquashfs4Size(buffer, 10, nullptr, nullptr));
+  memcpy(buffer, kSquashfsFile, sizeof(kSquashfsFile));
+
+  // Modify the bytes_used to have 6 blocks.
+  int64_t* bytes_used = reinterpret_cast<int64_t*>(buffer + 0x28);
+  *bytes_used = 4096 * 5 + 1;  // 6 "blocks".
+  EXPECT_TRUE(utils::GetSquashfs4Size(buffer, sizeof(kSquashfsFile),
+                                      &block_count, &block_size));
+  EXPECT_EQ(4096, block_size);
+  EXPECT_EQ(6, block_count);
+}
+
+namespace {
+void GetFileFormatTester(const string& expected,
+                         const vector<uint8_t>& contents) {
+  test_utils::ScopedTempFile file;
+  ASSERT_TRUE(utils::WriteFile(file.GetPath().c_str(),
+                               reinterpret_cast<const char*>(contents.data()),
+                               contents.size()));
+  EXPECT_EQ(expected, utils::GetFileFormat(file.GetPath()));
+}
+}  // namespace
+
+TEST(UtilsTest, GetFileFormatTest) {
+  EXPECT_EQ("File not found.", utils::GetFileFormat("/path/to/nowhere"));
+  GetFileFormatTester("data", vector<uint8_t>{1, 2, 3, 4, 5, 6, 7, 8});
+  GetFileFormatTester("ELF", vector<uint8_t>{0x7f, 0x45, 0x4c, 0x46});
+
+  // Real tests from cros_installer on different boards.
+  // ELF 32-bit LSB executable, Intel 80386
+  GetFileFormatTester(
+      "ELF 32-bit little-endian x86",
+      vector<uint8_t>{0x7f, 0x45, 0x4c, 0x46, 0x01, 0x01, 0x01, 0x00,
+                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+                      0x02, 0x00, 0x03, 0x00, 0x01, 0x00, 0x00, 0x00,
+                      0x90, 0x83, 0x04, 0x08, 0x34, 0x00, 0x00, 0x00});
+
+  // ELF 32-bit LSB executable, MIPS
+  GetFileFormatTester(
+      "ELF 32-bit little-endian mips",
+      vector<uint8_t>{0x7f, 0x45, 0x4c, 0x46, 0x01, 0x01, 0x01, 0x00,
+                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+                      0x03, 0x00, 0x08, 0x00, 0x01, 0x00, 0x00, 0x00,
+                      0xc0, 0x12, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00});
+
+  // ELF 32-bit LSB executable, ARM
+  GetFileFormatTester(
+      "ELF 32-bit little-endian arm",
+      vector<uint8_t>{0x7f, 0x45, 0x4c, 0x46, 0x01, 0x01, 0x01, 0x00,
+                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+                      0x02, 0x00, 0x28, 0x00, 0x01, 0x00, 0x00, 0x00,
+                      0x85, 0x8b, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00});
+
+  // ELF 64-bit LSB executable, x86-64
+  GetFileFormatTester(
+      "ELF 64-bit little-endian x86-64",
+      vector<uint8_t>{0x7f, 0x45, 0x4c, 0x46, 0x02, 0x01, 0x01, 0x00,
+                      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+                      0x02, 0x00, 0x3e, 0x00, 0x01, 0x00, 0x00, 0x00,
+                      0xb0, 0x04, 0x40, 0x00, 0x00, 0x00, 0x00, 0x00});
+}
+
+TEST(UtilsTest, ScheduleCrashReporterUploadTest) {
+  // Not much to test. At least this tests for memory leaks, crashes,
+  // log errors.
+  FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+  utils::ScheduleCrashReporterUpload();
+  // Test that we scheduled one callback from the crash reporter.
+  EXPECT_EQ(1, brillo::MessageLoopRunMaxIterations(&loop, 100));
+  EXPECT_FALSE(loop.PendingTasks());
+}
+
+TEST(UtilsTest, FormatTimeDeltaTest) {
+  // utils::FormatTimeDelta() is not locale-aware (it's only used for logging
+  // which is not localized) so we only need to test the C locale
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromMilliseconds(100)),
+            "0.1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(0)),
+            "0s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(1)),
+            "1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(59)),
+            "59s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(60)),
+            "1m0s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(61)),
+            "1m1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(90)),
+            "1m30s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(1205)),
+            "20m5s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(3600)),
+            "1h0m0s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(3601)),
+            "1h0m1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(3661)),
+            "1h1m1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(7261)),
+            "2h1m1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(86400)),
+            "1d0h0m0s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(86401)),
+            "1d0h0m1s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(200000)),
+            "2d7h33m20s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(200000) +
+                                   base::TimeDelta::FromMilliseconds(1)),
+            "2d7h33m20.001s");
+  EXPECT_EQ(utils::FormatTimeDelta(base::TimeDelta::FromSeconds(-1)),
+            "-1s");
+}
+
+TEST(UtilsTest, TimeFromStructTimespecTest) {
+  struct timespec ts;
+
+  // Unix epoch (Thursday 00:00:00 UTC on Jan 1, 1970)
+  ts = (struct timespec) {.tv_sec = 0, .tv_nsec = 0};
+  EXPECT_EQ(base::Time::UnixEpoch(), utils::TimeFromStructTimespec(&ts));
+
+  // 42 ms after the Unix billennium (Sunday 01:46:40 UTC on September 9, 2001)
+  ts = (struct timespec) {.tv_sec = 1000 * 1000 * 1000,
+                          .tv_nsec = 42 * 1000 * 1000};
+  base::Time::Exploded exploded = (base::Time::Exploded) {
+    .year = 2001, .month = 9, .day_of_week = 0, .day_of_month = 9,
+    .hour = 1, .minute = 46, .second = 40, .millisecond = 42};
+  EXPECT_EQ(base::Time::FromUTCExploded(exploded),
+            utils::TimeFromStructTimespec(&ts));
+}
+
+TEST(UtilsTest, DecodeAndStoreBase64String) {
+  base::FilePath path;
+
+  // Ensure we return false on empty strings or invalid base64.
+  EXPECT_FALSE(utils::DecodeAndStoreBase64String("", &path));
+  EXPECT_FALSE(utils::DecodeAndStoreBase64String("not valid base64", &path));
+
+  // Pass known base64 and check that it matches. This string was generated
+  // the following way:
+  //
+  //   $ echo "Update Engine" | base64
+  //   VXBkYXRlIEVuZ2luZQo=
+  EXPECT_TRUE(utils::DecodeAndStoreBase64String("VXBkYXRlIEVuZ2luZQo=",
+                                                &path));
+  ScopedPathUnlinker unlinker(path.value());
+  string expected_contents = "Update Engine\n";
+  string contents;
+  EXPECT_TRUE(utils::ReadFile(path.value(), &contents));
+  EXPECT_EQ(contents, expected_contents);
+  EXPECT_EQ(utils::FileSize(path.value()), expected_contents.size());
+}
+
+TEST(UtilsTest, ConvertToOmahaInstallDate) {
+  // The Omaha Epoch starts at Jan 1, 2007 0:00 PST which is a
+  // Monday. In Unix time, this point in time is easily obtained via
+  // the date(1) command like this:
+  //
+  //  $ date +"%s" --date="Jan 1, 2007 0:00 PST"
+  const time_t omaha_epoch = 1167638400;
+  int value;
+
+  // Points in time *on and after* the Omaha epoch should not fail.
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch), &value));
+  EXPECT_GE(value, 0);
+
+  // Anything before the Omaha epoch should fail. We test it for two points.
+  EXPECT_FALSE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch - 1), &value));
+  EXPECT_FALSE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch - 100*24*3600), &value));
+
+  // Check that we jump from 0 to 7 exactly on the one-week mark, e.g.
+  // on Jan 8, 2007 0:00 PST.
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 7*24*3600 - 1), &value));
+  EXPECT_EQ(value, 0);
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 7*24*3600), &value));
+  EXPECT_EQ(value, 7);
+
+  // Check a couple of more values.
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 10*24*3600), &value));
+  EXPECT_EQ(value, 7);
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 20*24*3600), &value));
+  EXPECT_EQ(value, 14);
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 26*24*3600), &value));
+  EXPECT_EQ(value, 21);
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(omaha_epoch + 29*24*3600), &value));
+  EXPECT_EQ(value, 28);
+
+  // The date Jun 4, 2007 0:00 PDT is a Monday and is hence a point
+  // where the Omaha InstallDate jumps 7 days. Its unix time is
+  // 1180940400. Notably, this is a point in time where Daylight
+  // Savings Time (DST) was is in effect (e.g. it's PDT, not PST).
+  //
+  // Note that as utils::ConvertToOmahaInstallDate() _deliberately_
+  // ignores DST (as it's hard to implement in a thread-safe way using
+  // glibc, see comments in utils.h) we have to fudge by the DST
+  // offset which is one hour. Conveniently, if the function were
+  // someday modified to be DST aware, this test would have to be
+  // modified as well.
+  const time_t dst_time = 1180940400;  // Jun 4, 2007 0:00 PDT.
+  const time_t fudge = 3600;
+  int value1, value2;
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(dst_time + fudge - 1), &value1));
+  EXPECT_TRUE(utils::ConvertToOmahaInstallDate(
+      base::Time::FromTimeT(dst_time + fudge), &value2));
+  EXPECT_EQ(value1, value2 - 7);
+}
+
+TEST(UtilsTest, GetMinorVersion) {
+  // Test GetMinorVersion by verifying that it parses the conf file and returns
+  // the correct value.
+  uint32_t minor_version;
+
+  brillo::KeyValueStore store;
+  EXPECT_FALSE(utils::GetMinorVersion(store, &minor_version));
+
+  EXPECT_TRUE(store.LoadFromString("PAYLOAD_MINOR_VERSION=one-two-three\n"));
+  EXPECT_FALSE(utils::GetMinorVersion(store, &minor_version));
+
+  EXPECT_TRUE(store.LoadFromString("PAYLOAD_MINOR_VERSION=123\n"));
+  EXPECT_TRUE(utils::GetMinorVersion(store, &minor_version));
+  EXPECT_EQ(minor_version, 123);
+}
+
+static bool BoolMacroTestHelper() {
+  int i = 1;
+  unsigned int ui = 1;
+  bool b = 1;
+  std::unique_ptr<char> cptr(new char);
+
+  TEST_AND_RETURN_FALSE(i);
+  TEST_AND_RETURN_FALSE(ui);
+  TEST_AND_RETURN_FALSE(b);
+  TEST_AND_RETURN_FALSE(cptr);
+
+  TEST_AND_RETURN_FALSE_ERRNO(i);
+  TEST_AND_RETURN_FALSE_ERRNO(ui);
+  TEST_AND_RETURN_FALSE_ERRNO(b);
+  TEST_AND_RETURN_FALSE_ERRNO(cptr);
+
+  return true;
+}
+
+static void VoidMacroTestHelper(bool* ret) {
+  int i = 1;
+  unsigned int ui = 1;
+  bool b = 1;
+  std::unique_ptr<char> cptr(new char);
+
+  *ret = false;
+
+  TEST_AND_RETURN(i);
+  TEST_AND_RETURN(ui);
+  TEST_AND_RETURN(b);
+  TEST_AND_RETURN(cptr);
+
+  TEST_AND_RETURN_ERRNO(i);
+  TEST_AND_RETURN_ERRNO(ui);
+  TEST_AND_RETURN_ERRNO(b);
+  TEST_AND_RETURN_ERRNO(cptr);
+
+  *ret = true;
+}
+
+TEST(UtilsTest, TestMacros) {
+  bool void_test = false;
+  VoidMacroTestHelper(&void_test);
+  EXPECT_TRUE(void_test);
+
+  EXPECT_TRUE(BoolMacroTestHelper());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/connection_manager.cc b/connection_manager.cc
new file mode 100644
index 0000000..778cba5
--- /dev/null
+++ b/connection_manager.cc
@@ -0,0 +1,245 @@
+//
+// Copyright (C) 2012 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 "update_engine/connection_manager.h"
+
+#include <set>
+#include <string>
+
+#include <base/stl_util.h>
+#include <base/strings/string_util.h>
+#include <policy/device_policy.h>
+#include <shill/dbus-constants.h>
+#include <shill/dbus-proxies.h>
+
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/system_state.h"
+
+using org::chromium::flimflam::ManagerProxyInterface;
+using org::chromium::flimflam::ServiceProxyInterface;
+using std::set;
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+NetworkConnectionType ParseConnectionType(const string& type_str) {
+  if (type_str == shill::kTypeEthernet) {
+    return NetworkConnectionType::kEthernet;
+  } else if (type_str == shill::kTypeWifi) {
+    return NetworkConnectionType::kWifi;
+  } else if (type_str == shill::kTypeWimax) {
+    return NetworkConnectionType::kWimax;
+  } else if (type_str == shill::kTypeBluetooth) {
+    return NetworkConnectionType::kBluetooth;
+  } else if (type_str == shill::kTypeCellular) {
+    return NetworkConnectionType::kCellular;
+  }
+  return NetworkConnectionType::kUnknown;
+}
+
+NetworkTethering ParseTethering(const string& tethering_str) {
+  if (tethering_str == shill::kTetheringNotDetectedState) {
+    return NetworkTethering::kNotDetected;
+  } else if (tethering_str == shill::kTetheringSuspectedState) {
+    return NetworkTethering::kSuspected;
+  } else if (tethering_str == shill::kTetheringConfirmedState) {
+    return NetworkTethering::kConfirmed;
+  }
+  LOG(WARNING) << "Unknown Tethering value: " << tethering_str;
+  return NetworkTethering::kUnknown;
+}
+
+}  // namespace
+
+ConnectionManager::ConnectionManager(ShillProxyInterface* shill_proxy,
+                                     SystemState* system_state)
+    : shill_proxy_(shill_proxy), system_state_(system_state) {}
+
+bool ConnectionManager::IsUpdateAllowedOver(NetworkConnectionType type,
+                                            NetworkTethering tethering) const {
+  switch (type) {
+    case NetworkConnectionType::kBluetooth:
+      return false;
+
+    case NetworkConnectionType::kCellular: {
+      set<string> allowed_types;
+      const policy::DevicePolicy* device_policy =
+          system_state_->device_policy();
+
+      // A device_policy is loaded in a lazy way right before an update check,
+      // so the device_policy should be already loaded at this point. If it's
+      // not, return a safe value for this setting.
+      if (!device_policy) {
+        LOG(INFO) << "Disabling updates over cellular networks as there's no "
+                     "device policy loaded yet.";
+        return false;
+      }
+
+      if (device_policy->GetAllowedConnectionTypesForUpdate(&allowed_types)) {
+        // The update setting is enforced by the device policy.
+
+        if (!ContainsKey(allowed_types, shill::kTypeCellular)) {
+          LOG(INFO) << "Disabling updates over cellular connection as it's not "
+                       "allowed in the device policy.";
+          return false;
+        }
+
+        LOG(INFO) << "Allowing updates over cellular per device policy.";
+        return true;
+      } else {
+        // There's no update setting in the device policy, using the local user
+        // setting.
+        PrefsInterface* prefs = system_state_->prefs();
+
+        if (!prefs || !prefs->Exists(kPrefsUpdateOverCellularPermission)) {
+          LOG(INFO) << "Disabling updates over cellular connection as there's "
+                       "no device policy setting nor user preference present.";
+          return false;
+        }
+
+        bool stored_value;
+        if (!prefs->GetBoolean(kPrefsUpdateOverCellularPermission,
+                               &stored_value)) {
+          return false;
+        }
+
+        if (!stored_value) {
+          LOG(INFO) << "Disabling updates over cellular connection per user "
+                       "setting.";
+          return false;
+        }
+        LOG(INFO) << "Allowing updates over cellular per user setting.";
+        return true;
+      }
+    }
+
+    default:
+      if (tethering == NetworkTethering::kConfirmed) {
+        // Treat this connection as if it is a cellular connection.
+        LOG(INFO) << "Current connection is confirmed tethered, using Cellular "
+                     "setting.";
+        return IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                   NetworkTethering::kUnknown);
+      }
+      return true;
+  }
+}
+
+// static
+const char* ConnectionManager::StringForConnectionType(
+    NetworkConnectionType type) {
+  switch (type) {
+    case NetworkConnectionType::kEthernet:
+      return shill::kTypeEthernet;
+    case NetworkConnectionType::kWifi:
+      return shill::kTypeWifi;
+    case NetworkConnectionType::kWimax:
+      return shill::kTypeWimax;
+    case NetworkConnectionType::kBluetooth:
+      return shill::kTypeBluetooth;
+    case NetworkConnectionType::kCellular:
+      return shill::kTypeCellular;
+    case NetworkConnectionType::kUnknown:
+      return "Unknown";
+  }
+  return "Unknown";
+}
+
+bool ConnectionManager::GetConnectionProperties(
+    NetworkConnectionType* out_type,
+    NetworkTethering* out_tethering) {
+  dbus::ObjectPath default_service_path;
+  TEST_AND_RETURN_FALSE(GetDefaultServicePath(&default_service_path));
+  if (!default_service_path.IsValid())
+    return false;
+  // Shill uses the "/" service path to indicate that it is not connected.
+  if (default_service_path.value() == "/")
+    return false;
+  TEST_AND_RETURN_FALSE(
+      GetServicePathProperties(default_service_path, out_type, out_tethering));
+  return true;
+}
+
+bool ConnectionManager::GetDefaultServicePath(dbus::ObjectPath* out_path) {
+  brillo::VariantDictionary properties;
+  brillo::ErrorPtr error;
+  ManagerProxyInterface* manager_proxy = shill_proxy_->GetManagerProxy();
+  if (!manager_proxy)
+    return false;
+  TEST_AND_RETURN_FALSE(manager_proxy->GetProperties(&properties, &error));
+
+  const auto& prop_default_service =
+      properties.find(shill::kDefaultServiceProperty);
+  if (prop_default_service == properties.end())
+    return false;
+
+  *out_path = prop_default_service->second.TryGet<dbus::ObjectPath>();
+  return out_path->IsValid();
+}
+
+bool ConnectionManager::GetServicePathProperties(
+    const dbus::ObjectPath& path,
+    NetworkConnectionType* out_type,
+    NetworkTethering* out_tethering) {
+  // We create and dispose the ServiceProxyInterface on every request.
+  std::unique_ptr<ServiceProxyInterface> service =
+      shill_proxy_->GetServiceForPath(path);
+
+  brillo::VariantDictionary properties;
+  brillo::ErrorPtr error;
+  TEST_AND_RETURN_FALSE(service->GetProperties(&properties, &error));
+
+  // Populate the out_tethering.
+  const auto& prop_tethering = properties.find(shill::kTetheringProperty);
+  if (prop_tethering == properties.end()) {
+    // Set to Unknown if not present.
+    *out_tethering = NetworkTethering::kUnknown;
+  } else {
+    // If the property doesn't contain a string value, the empty string will
+    // become kUnknown.
+    *out_tethering = ParseTethering(prop_tethering->second.TryGet<string>());
+  }
+
+  // Populate the out_type property.
+  const auto& prop_type = properties.find(shill::kTypeProperty);
+  if (prop_type == properties.end()) {
+    // Set to Unknown if not present.
+    *out_type = NetworkConnectionType::kUnknown;
+    return false;
+  }
+
+  string type_str = prop_type->second.TryGet<string>();
+  if (type_str == shill::kTypeVPN) {
+    const auto& prop_physical =
+        properties.find(shill::kPhysicalTechnologyProperty);
+    if (prop_physical == properties.end()) {
+      LOG(ERROR) << "No PhysicalTechnology property found for a VPN"
+                    " connection (service: "
+                 << path.value() << "). Returning default kUnknown value.";
+      *out_type = NetworkConnectionType::kUnknown;
+    } else {
+      *out_type = ParseConnectionType(prop_physical->second.TryGet<string>());
+    }
+  } else {
+    *out_type = ParseConnectionType(type_str);
+  }
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/connection_manager.h b/connection_manager.h
new file mode 100644
index 0000000..2057f3b
--- /dev/null
+++ b/connection_manager.h
@@ -0,0 +1,73 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_CONNECTION_MANAGER_H_
+#define UPDATE_ENGINE_CONNECTION_MANAGER_H_
+
+#include <string>
+
+#include <base/macros.h>
+#include <dbus/object_path.h>
+
+#include "update_engine/connection_manager_interface.h"
+#include "update_engine/shill_proxy_interface.h"
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+// This class implements the concrete class that talks with the connection
+// manager (shill) over DBus.
+// TODO(deymo): Remove this class and use ShillProvider from the UpdateManager.
+class ConnectionManager : public ConnectionManagerInterface {
+ public:
+  // Returns the string representation corresponding to the given
+  // connection type.
+  static const char* StringForConnectionType(NetworkConnectionType type);
+
+  // Constructs a new ConnectionManager object initialized with the
+  // given system state.
+  ConnectionManager(ShillProxyInterface* shill_proxy,
+                    SystemState* system_state);
+  ~ConnectionManager() override = default;
+
+  // ConnectionManagerInterface overrides.
+  bool GetConnectionProperties(NetworkConnectionType* out_type,
+                               NetworkTethering* out_tethering) override;
+  bool IsUpdateAllowedOver(NetworkConnectionType type,
+                           NetworkTethering tethering) const override;
+
+ private:
+  // Returns (via out_path) the default network path, or empty string if
+  // there's no network up. Returns true on success.
+  bool GetDefaultServicePath(dbus::ObjectPath* out_path);
+
+  bool GetServicePathProperties(const dbus::ObjectPath& path,
+                                NetworkConnectionType* out_type,
+                                NetworkTethering* out_tethering);
+
+  // The mockable interface to access the shill DBus proxies.
+  ShillProxyInterface* shill_proxy_;
+
+  // The global context for update_engine.
+  SystemState* system_state_;
+
+  DISALLOW_COPY_AND_ASSIGN(ConnectionManager);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_CONNECTION_MANAGER_H_
diff --git a/connection_manager_interface.h b/connection_manager_interface.h
new file mode 100644
index 0000000..cb60a3c
--- /dev/null
+++ b/connection_manager_interface.h
@@ -0,0 +1,68 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_CONNECTION_MANAGER_INTERFACE_H_
+#define UPDATE_ENGINE_CONNECTION_MANAGER_INTERFACE_H_
+
+#include <base/macros.h>
+
+namespace chromeos_update_engine {
+
+enum class NetworkConnectionType {
+  kEthernet,
+  kWifi,
+  kWimax,
+  kBluetooth,
+  kCellular,
+  kUnknown
+};
+
+enum class NetworkTethering {
+  kNotDetected,
+  kSuspected,
+  kConfirmed,
+  kUnknown
+};
+
+// This class exposes a generic interface to the connection manager
+// (e.g FlimFlam, Shill, etc.) to consolidate all connection-related
+// logic in update_engine.
+class ConnectionManagerInterface {
+ public:
+  virtual ~ConnectionManagerInterface() = default;
+
+  // Populates |out_type| with the type of the network connection
+  // that we are currently connected and |out_tethering| with the estimate of
+  // whether that network is being tethered.
+  virtual bool GetConnectionProperties(NetworkConnectionType* out_type,
+                                       NetworkTethering* out_tethering) = 0;
+
+  // Returns true if we're allowed to update the system when we're
+  // connected to the internet through the given network connection type and the
+  // given tethering state.
+  virtual bool IsUpdateAllowedOver(NetworkConnectionType type,
+                                   NetworkTethering tethering) const = 0;
+
+ protected:
+  ConnectionManagerInterface() = default;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ConnectionManagerInterface);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_CONNECTION_MANAGER_INTERFACE_H_
diff --git a/connection_manager_unittest.cc b/connection_manager_unittest.cc
new file mode 100644
index 0000000..612929b
--- /dev/null
+++ b/connection_manager_unittest.cc
@@ -0,0 +1,409 @@
+//
+// Copyright (C) 2012 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 "update_engine/connection_manager.h"
+
+#include <set>
+#include <string>
+
+#include <base/logging.h>
+#include <brillo/any.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/variant_dictionary.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <shill/dbus-constants.h>
+#include <shill/dbus-proxies.h>
+#include <shill/dbus-proxy-mocks.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/fake_shill_proxy.h"
+#include "update_engine/fake_system_state.h"
+
+using org::chromium::flimflam::ManagerProxyMock;
+using org::chromium::flimflam::ServiceProxyMock;
+using std::set;
+using std::string;
+using testing::Return;
+using testing::SetArgPointee;
+using testing::_;
+
+namespace chromeos_update_engine {
+
+class ConnectionManagerTest : public ::testing::Test {
+ public:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    fake_system_state_.set_connection_manager(&cmut_);
+  }
+
+  void TearDown() override { EXPECT_FALSE(loop_.PendingTasks()); }
+
+ protected:
+  // Sets the default_service object path in the response from the
+  // ManagerProxyMock instance.
+  void SetManagerReply(const char* default_service, bool reply_succeeds);
+
+  // Sets the |service_type|, |physical_technology| and |service_tethering|
+  // properties in the mocked service |service_path|. If any of the three
+  // const char* is a nullptr, the corresponding property will not be included
+  // in the response.
+  void SetServiceReply(const string& service_path,
+                       const char* service_type,
+                       const char* physical_technology,
+                       const char* service_tethering);
+
+  void TestWithServiceType(
+      const char* service_type,
+      const char* physical_technology,
+      NetworkConnectionType expected_type);
+  void TestWithServiceTethering(
+      const char* service_tethering,
+      NetworkTethering expected_tethering);
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  FakeSystemState fake_system_state_;
+  FakeShillProxy fake_shill_proxy_;
+
+  // ConnectionManager under test.
+  ConnectionManager cmut_{&fake_shill_proxy_, &fake_system_state_};
+};
+
+void ConnectionManagerTest::SetManagerReply(const char* default_service,
+                                            bool reply_succeeds) {
+  ManagerProxyMock* manager_proxy_mock = fake_shill_proxy_.GetManagerProxy();
+  if (!reply_succeeds) {
+    EXPECT_CALL(*manager_proxy_mock, GetProperties(_, _, _))
+        .WillOnce(Return(false));
+    return;
+  }
+
+  // Create a dictionary of properties and optionally include the default
+  // service.
+  brillo::VariantDictionary reply_dict;
+  reply_dict["SomeOtherProperty"] = 0xC0FFEE;
+
+  if (default_service) {
+    reply_dict[shill::kDefaultServiceProperty] =
+        dbus::ObjectPath(default_service);
+  }
+  EXPECT_CALL(*manager_proxy_mock, GetProperties(_, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(reply_dict), Return(true)));
+}
+
+void ConnectionManagerTest::SetServiceReply(const string& service_path,
+                                            const char* service_type,
+                                            const char* physical_technology,
+                                            const char* service_tethering) {
+  brillo::VariantDictionary reply_dict;
+  reply_dict["SomeOtherProperty"] = 0xC0FFEE;
+
+  if (service_type)
+    reply_dict[shill::kTypeProperty] = string(service_type);
+
+  if (physical_technology) {
+    reply_dict[shill::kPhysicalTechnologyProperty] =
+        string(physical_technology);
+  }
+
+  if (service_tethering)
+    reply_dict[shill::kTetheringProperty] = string(service_tethering);
+
+  std::unique_ptr<ServiceProxyMock> service_proxy_mock(new ServiceProxyMock());
+
+  // Plumb return value into mock object.
+  EXPECT_CALL(*service_proxy_mock.get(), GetProperties(_, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(reply_dict), Return(true)));
+
+  fake_shill_proxy_.SetServiceForPath(dbus::ObjectPath(service_path),
+                                      std::move(service_proxy_mock));
+}
+
+void ConnectionManagerTest::TestWithServiceType(
+    const char* service_type,
+    const char* physical_technology,
+    NetworkConnectionType expected_type) {
+  SetManagerReply("/service/guest/network", true);
+  SetServiceReply("/service/guest/network",
+                  service_type,
+                  physical_technology,
+                  shill::kTetheringNotDetectedState);
+
+  NetworkConnectionType type;
+  NetworkTethering tethering;
+  EXPECT_TRUE(cmut_.GetConnectionProperties(&type, &tethering));
+  EXPECT_EQ(expected_type, type);
+  testing::Mock::VerifyAndClearExpectations(
+      fake_shill_proxy_.GetManagerProxy());
+}
+
+void ConnectionManagerTest::TestWithServiceTethering(
+    const char* service_tethering,
+    NetworkTethering expected_tethering) {
+  SetManagerReply("/service/guest/network", true);
+  SetServiceReply(
+      "/service/guest/network", shill::kTypeWifi, nullptr, service_tethering);
+
+  NetworkConnectionType type;
+  NetworkTethering tethering;
+  EXPECT_TRUE(cmut_.GetConnectionProperties(&type, &tethering));
+  EXPECT_EQ(expected_tethering, tethering);
+  testing::Mock::VerifyAndClearExpectations(
+      fake_shill_proxy_.GetManagerProxy());
+}
+
+TEST_F(ConnectionManagerTest, SimpleTest) {
+  TestWithServiceType(shill::kTypeEthernet, nullptr,
+                      NetworkConnectionType::kEthernet);
+  TestWithServiceType(shill::kTypeWifi, nullptr,
+                      NetworkConnectionType::kWifi);
+  TestWithServiceType(shill::kTypeWimax, nullptr,
+                      NetworkConnectionType::kWimax);
+  TestWithServiceType(shill::kTypeBluetooth, nullptr,
+                      NetworkConnectionType::kBluetooth);
+  TestWithServiceType(shill::kTypeCellular, nullptr,
+                      NetworkConnectionType::kCellular);
+}
+
+TEST_F(ConnectionManagerTest, PhysicalTechnologyTest) {
+  TestWithServiceType(shill::kTypeVPN, nullptr,
+                      NetworkConnectionType::kUnknown);
+  TestWithServiceType(shill::kTypeVPN, shill::kTypeVPN,
+                      NetworkConnectionType::kUnknown);
+  TestWithServiceType(shill::kTypeVPN, shill::kTypeWifi,
+                      NetworkConnectionType::kWifi);
+  TestWithServiceType(shill::kTypeVPN, shill::kTypeWimax,
+                      NetworkConnectionType::kWimax);
+}
+
+TEST_F(ConnectionManagerTest, TetheringTest) {
+  TestWithServiceTethering(shill::kTetheringConfirmedState,
+                           NetworkTethering::kConfirmed);
+  TestWithServiceTethering(shill::kTetheringNotDetectedState,
+                           NetworkTethering::kNotDetected);
+  TestWithServiceTethering(shill::kTetheringSuspectedState,
+                           NetworkTethering::kSuspected);
+  TestWithServiceTethering("I'm not a valid property value =)",
+                           NetworkTethering::kUnknown);
+}
+
+TEST_F(ConnectionManagerTest, UnknownTest) {
+  TestWithServiceType("foo", nullptr, NetworkConnectionType::kUnknown);
+}
+
+TEST_F(ConnectionManagerTest, AllowUpdatesOverEthernetTest) {
+  // Updates over Ethernet are allowed even if there's no policy.
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kEthernet,
+                                        NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, AllowUpdatesOverWifiTest) {
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWifi,
+                                        NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, AllowUpdatesOverWimaxTest) {
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWimax,
+                                        NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, BlockUpdatesOverBluetoothTest) {
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kBluetooth,
+                                         NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, AllowUpdatesOnlyOver3GPerPolicyTest) {
+  policy::MockDevicePolicy allow_3g_policy;
+
+  fake_system_state_.set_device_policy(&allow_3g_policy);
+
+  // This test tests cellular (3G) being the only connection type being allowed.
+  set<string> allowed_set;
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kCellular));
+
+  EXPECT_CALL(allow_3g_policy, GetAllowedConnectionTypesForUpdate(_))
+      .Times(1)
+      .WillOnce(DoAll(SetArgPointee<0>(allowed_set), Return(true)));
+
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                        NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, AllowUpdatesOver3GAndOtherTypesPerPolicyTest) {
+  policy::MockDevicePolicy allow_3g_policy;
+
+  fake_system_state_.set_device_policy(&allow_3g_policy);
+
+  // This test tests multiple connection types being allowed, with
+  // 3G one among them. Only Cellular is currently enforced by the policy
+  // setting, the others are ignored (see Bluetooth for example).
+  set<string> allowed_set;
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kCellular));
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kBluetooth));
+
+  EXPECT_CALL(allow_3g_policy, GetAllowedConnectionTypesForUpdate(_))
+      .Times(3)
+      .WillRepeatedly(DoAll(SetArgPointee<0>(allowed_set), Return(true)));
+
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kEthernet,
+                                        NetworkTethering::kUnknown));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kEthernet,
+                                        NetworkTethering::kNotDetected));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                        NetworkTethering::kUnknown));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWifi,
+                                        NetworkTethering::kUnknown));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWimax,
+                                        NetworkTethering::kUnknown));
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kBluetooth,
+                                         NetworkTethering::kUnknown));
+
+  // Tethered networks are treated in the same way as Cellular networks and
+  // thus allowed.
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kEthernet,
+                                        NetworkTethering::kConfirmed));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWifi,
+                                        NetworkTethering::kConfirmed));
+}
+
+TEST_F(ConnectionManagerTest, BlockUpdatesOverCellularByDefaultTest) {
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                         NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, BlockUpdatesOverTetheredNetworkByDefaultTest) {
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWifi,
+                                         NetworkTethering::kConfirmed));
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kEthernet,
+                                         NetworkTethering::kConfirmed));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kWifi,
+                                        NetworkTethering::kSuspected));
+}
+
+TEST_F(ConnectionManagerTest, BlockUpdatesOver3GPerPolicyTest) {
+  policy::MockDevicePolicy block_3g_policy;
+
+  fake_system_state_.set_device_policy(&block_3g_policy);
+
+  // Test that updates for 3G are blocked while updates are allowed
+  // over several other types.
+  set<string> allowed_set;
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kEthernet));
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kWifi));
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kWimax));
+
+  EXPECT_CALL(block_3g_policy, GetAllowedConnectionTypesForUpdate(_))
+      .Times(1)
+      .WillOnce(DoAll(SetArgPointee<0>(allowed_set), Return(true)));
+
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                         NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, BlockUpdatesOver3GIfErrorInPolicyFetchTest) {
+  policy::MockDevicePolicy allow_3g_policy;
+
+  fake_system_state_.set_device_policy(&allow_3g_policy);
+
+  set<string> allowed_set;
+  allowed_set.insert(
+      cmut_.StringForConnectionType(NetworkConnectionType::kCellular));
+
+  // Return false for GetAllowedConnectionTypesForUpdate and see
+  // that updates are still blocked for 3G despite the value being in
+  // the string set above.
+  EXPECT_CALL(allow_3g_policy, GetAllowedConnectionTypesForUpdate(_))
+      .Times(1)
+      .WillOnce(DoAll(SetArgPointee<0>(allowed_set), Return(false)));
+
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                         NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, UseUserPrefForUpdatesOverCellularIfNoPolicyTest) {
+  policy::MockDevicePolicy no_policy;
+  testing::NiceMock<MockPrefs>* prefs = fake_system_state_.mock_prefs();
+
+  fake_system_state_.set_device_policy(&no_policy);
+
+  // No setting enforced by the device policy, user prefs should be used.
+  EXPECT_CALL(no_policy, GetAllowedConnectionTypesForUpdate(_))
+      .Times(3)
+      .WillRepeatedly(Return(false));
+
+  // No user pref: block.
+  EXPECT_CALL(*prefs, Exists(kPrefsUpdateOverCellularPermission))
+      .Times(1)
+      .WillOnce(Return(false));
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                         NetworkTethering::kUnknown));
+
+  // Allow per user pref.
+  EXPECT_CALL(*prefs, Exists(kPrefsUpdateOverCellularPermission))
+      .Times(1)
+      .WillOnce(Return(true));
+  EXPECT_CALL(*prefs, GetBoolean(kPrefsUpdateOverCellularPermission, _))
+      .Times(1)
+      .WillOnce(DoAll(SetArgPointee<1>(true), Return(true)));
+  EXPECT_TRUE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                        NetworkTethering::kUnknown));
+
+  // Block per user pref.
+  EXPECT_CALL(*prefs, Exists(kPrefsUpdateOverCellularPermission))
+      .Times(1)
+      .WillOnce(Return(true));
+  EXPECT_CALL(*prefs, GetBoolean(kPrefsUpdateOverCellularPermission, _))
+      .Times(1)
+      .WillOnce(DoAll(SetArgPointee<1>(false), Return(true)));
+  EXPECT_FALSE(cmut_.IsUpdateAllowedOver(NetworkConnectionType::kCellular,
+                                         NetworkTethering::kUnknown));
+}
+
+TEST_F(ConnectionManagerTest, StringForConnectionTypeTest) {
+  EXPECT_STREQ(shill::kTypeEthernet,
+               cmut_.StringForConnectionType(NetworkConnectionType::kEthernet));
+  EXPECT_STREQ(shill::kTypeWifi,
+               cmut_.StringForConnectionType(NetworkConnectionType::kWifi));
+  EXPECT_STREQ(shill::kTypeWimax,
+               cmut_.StringForConnectionType(NetworkConnectionType::kWimax));
+  EXPECT_STREQ(shill::kTypeBluetooth,
+               cmut_.StringForConnectionType(
+                   NetworkConnectionType::kBluetooth));
+  EXPECT_STREQ(shill::kTypeCellular,
+               cmut_.StringForConnectionType(NetworkConnectionType::kCellular));
+  EXPECT_STREQ("Unknown",
+               cmut_.StringForConnectionType(NetworkConnectionType::kUnknown));
+  EXPECT_STREQ("Unknown",
+               cmut_.StringForConnectionType(
+                   static_cast<NetworkConnectionType>(999999)));
+}
+
+TEST_F(ConnectionManagerTest, MalformedServiceList) {
+  SetManagerReply("/service/guest/network", false);
+
+  NetworkConnectionType type;
+  NetworkTethering tethering;
+  EXPECT_FALSE(cmut_.GetConnectionProperties(&type, &tethering));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/daemon.cc b/daemon.cc
new file mode 100644
index 0000000..0b13c18
--- /dev/null
+++ b/daemon.cc
@@ -0,0 +1,153 @@
+//
+// Copyright (C) 2015 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 "update_engine/daemon.h"
+
+#include <sysexits.h>
+
+#include <base/bind.h>
+#include <base/location.h>
+#include <base/time/time.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/clock.h"
+#include "update_engine/update_attempter.h"
+
+using brillo::MessageLoop;
+
+namespace {
+const int kDBusSystemMaxWaitSeconds = 2 * 60;
+}  // namespace
+
+namespace chromeos_update_engine {
+
+namespace {
+// Wait for passed |bus| DBus to be connected by attempting to connect it up to
+// |timeout| time. Returns whether the Connect() eventually succeeded.
+bool WaitForDBusSystem(dbus::Bus* bus, base::TimeDelta timeout) {
+  Clock clock;
+  base::Time deadline = clock.GetMonotonicTime() + timeout;
+
+  while (clock.GetMonotonicTime() < deadline) {
+    if (bus->Connect())
+      return true;
+    LOG(WARNING) << "Failed to get system bus, waiting.";
+    // Wait 1 second.
+    sleep(1);
+  }
+  LOG(ERROR) << "Failed to get system bus after " << timeout.InSeconds()
+             << " seconds.";
+  return false;
+}
+}  // namespace
+
+UpdateEngineDaemon::~UpdateEngineDaemon() {
+  UpdateAttempter* update_attempter = real_system_state_->update_attempter();
+  // Prevent any DBus communication from UpdateAttempter when shutting down the
+  // daemon.
+  if (update_attempter)
+    update_attempter->set_dbus_adaptor(nullptr);
+}
+
+int UpdateEngineDaemon::OnInit() {
+  // Register the |subprocess_| singleton with this Daemon as the signal
+  // handler.
+  subprocess_.Init(this);
+
+  // We use Daemon::OnInit() and not DBusDaemon::OnInit() to gracefully wait for
+  // the D-Bus connection for up two minutes to avoid re-spawning the daemon
+  // too fast causing thrashing if dbus-daemon is not running.
+  int exit_code = Daemon::OnInit();
+  if (exit_code != EX_OK)
+    return exit_code;
+
+  dbus::Bus::Options options;
+  options.bus_type = dbus::Bus::SYSTEM;
+  bus_ = new dbus::Bus(options);
+
+  // Wait for DBus to be ready and exit if it doesn't become available after
+  // the timeout.
+  if (!WaitForDBusSystem(
+          bus_.get(),
+          base::TimeDelta::FromSeconds(kDBusSystemMaxWaitSeconds))) {
+    // TODO(deymo): Make it possible to run update_engine even if dbus-daemon
+    // is not running or constantly crashing.
+    LOG(ERROR) << "Failed to initialize DBus, aborting.";
+    return 1;
+  }
+
+  CHECK(bus_->SetUpAsyncOperations());
+
+  // Initialize update engine global state but continue if something fails.
+  real_system_state_.reset(new RealSystemState(bus_));
+  LOG_IF(ERROR, !real_system_state_->Initialize())
+      << "Failed to initialize system state.";
+  UpdateAttempter* update_attempter = real_system_state_->update_attempter();
+  CHECK(update_attempter);
+
+  // Create the DBus service.
+  dbus_adaptor_.reset(new UpdateEngineAdaptor(real_system_state_.get(), bus_));
+  update_attempter->set_dbus_adaptor(dbus_adaptor_.get());
+
+  dbus_adaptor_->RegisterAsync(base::Bind(&UpdateEngineDaemon::OnDBusRegistered,
+                                          base::Unretained(this)));
+  LOG(INFO) << "Waiting for DBus object to be registered.";
+  return EX_OK;
+}
+
+void UpdateEngineDaemon::OnDBusRegistered(bool succeeded) {
+  if (!succeeded) {
+    LOG(ERROR) << "Registering the UpdateEngineAdaptor";
+    QuitWithExitCode(1);
+    return;
+  }
+
+  // Take ownership of the service now that everything is initialized. We need
+  // to this now and not before to avoid exposing a well known DBus service
+  // path that doesn't have the service it is supposed to implement.
+  if (!dbus_adaptor_->RequestOwnership()) {
+    LOG(ERROR) << "Unable to take ownership of the DBus service, is there "
+               << "other update_engine daemon running?";
+    QuitWithExitCode(1);
+    return;
+  }
+
+  // Initiate update checks.
+  UpdateAttempter* update_attempter = real_system_state_->update_attempter();
+  update_attempter->ScheduleUpdates();
+
+  // Update boot flags after 45 seconds.
+  MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&UpdateAttempter::UpdateBootFlags,
+                 base::Unretained(update_attempter)),
+      base::TimeDelta::FromSeconds(45));
+
+  // Broadcast the update engine status on startup to ensure consistent system
+  // state on crashes.
+  MessageLoop::current()->PostTask(FROM_HERE, base::Bind(
+      &UpdateAttempter::BroadcastStatus,
+      base::Unretained(update_attempter)));
+
+  // Run the UpdateEngineStarted() method on |update_attempter|.
+  MessageLoop::current()->PostTask(FROM_HERE, base::Bind(
+      &UpdateAttempter::UpdateEngineStarted,
+      base::Unretained(update_attempter)));
+
+  LOG(INFO) << "Finished initialization. Now running the loop.";
+}
+
+}  // namespace chromeos_update_engine
diff --git a/daemon.h b/daemon.h
new file mode 100644
index 0000000..66841f6
--- /dev/null
+++ b/daemon.h
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_DAEMON_H_
+#define UPDATE_ENGINE_DAEMON_H_
+
+#include <memory>
+#include <string>
+
+#include <brillo/daemons/dbus_daemon.h>
+
+#include "update_engine/common/subprocess.h"
+#include "update_engine/dbus_service.h"
+#include "update_engine/real_system_state.h"
+
+namespace chromeos_update_engine {
+
+class UpdateEngineDaemon : public brillo::DBusDaemon {
+ public:
+  UpdateEngineDaemon() = default;
+  ~UpdateEngineDaemon();
+
+ protected:
+  int OnInit() override;
+
+ private:
+  // Run from the main loop when the |dbus_adaptor_| object is registered. At
+  // this point we can request ownership of the DBus service name and continue
+  // initialization.
+  void OnDBusRegistered(bool succeeded);
+
+  // The Subprocess singleton class requires a brillo::MessageLoop in the
+  // current thread, so we need to initialize it from this class instead of
+  // the main() function.
+  Subprocess subprocess_;
+
+  std::unique_ptr<UpdateEngineAdaptor> dbus_adaptor_;
+
+  // The RealSystemState uses the previous classes so it should be defined last.
+  std::unique_ptr<RealSystemState> real_system_state_;
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateEngineDaemon);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_DAEMON_H_
diff --git a/dbus_bindings/dbus-service-config.json b/dbus_bindings/dbus-service-config.json
new file mode 100644
index 0000000..fdae3ba
--- /dev/null
+++ b/dbus_bindings/dbus-service-config.json
@@ -0,0 +1,3 @@
+{
+  "service_name": "org.chromium.UpdateEngine"
+}
diff --git a/dbus_bindings/org.chromium.LibCrosService.dbus-xml b/dbus_bindings/org.chromium.LibCrosService.dbus-xml
new file mode 100644
index 0000000..2ea8313
--- /dev/null
+++ b/dbus_bindings/org.chromium.LibCrosService.dbus-xml
@@ -0,0 +1,20 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+
+<node name="/org/chromium/LibCrosService"
+      xmlns:tp="http://telepathy.freedesktop.org/wiki/DbusSpec#extensions-v0">
+  <interface name="org.chromium.LibCrosServiceInterface">
+    <method name="ResolveNetworkProxy">
+      <arg name="source_url" type="s" direction="in" />
+      <arg name="signal_interface" type="s" direction="in" />
+      <arg name="signal_name" type="s" direction="in" />
+      <annotation name="org.chromium.DBus.Method.Kind" value="simple" />
+    </method>
+  </interface>
+  <interface name="org.chromium.UpdateEngineLibcrosProxyResolvedInterface">
+    <signal name="ProxyResolved">
+      <arg name="source_url" type="s" direction="out" />
+      <arg name="proxy_info" type="s" direction="out" />
+      <arg name="error_message" type="s" direction="out" />
+    </signal>
+  </interface>
+</node>
diff --git a/dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml b/dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml
new file mode 100644
index 0000000..bc4ec36
--- /dev/null
+++ b/dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml
@@ -0,0 +1,84 @@
+<?xml version="1.0" encoding="utf-8" ?>
+<node name="/org/chromium/UpdateEngine">
+  <interface name="org.chromium.UpdateEngineInterface">
+    <annotation name="org.freedesktop.DBus.GLib.CSymbol"
+                value="update_engine_service" />
+    <annotation name="org.freedesktop.DBus.GLib.ClientCSymbol"
+                value="update_engine_client" />
+    <method name="AttemptUpdate">
+      <arg type="s" name="app_version" direction="in" />
+      <arg type="s" name="omaha_url" direction="in" />
+    </method>
+    <!-- TODO(zeuthen,chromium:286399): Rename to AttemptUpdate and
+         update Chrome and other users of the AttemptUpdate() method
+         in lockstep.
+    -->
+    <method name="AttemptUpdateWithFlags">
+      <arg type="s" name="app_version" direction="in" />
+      <arg type="s" name="omaha_url" direction="in" />
+      <!-- See AttemptUpdateFlags enum in update_engine/dbus-constants.h. -->
+      <arg type="i" name="flags" direction="in" />
+    </method>
+    <method name="AttemptRollback">
+      <arg type="b" name="powerwash" direction="in" />
+    </method>
+    <method name="CanRollback">
+      <arg type="b" name="can_rollback" direction="out" />
+    </method>
+    <method name="ResetStatus">
+    </method>
+    <method name="GetStatus">
+      <arg type="x" name="last_checked_time" direction="out" />
+      <arg type="d" name="progress" direction="out" />
+      <arg type="s" name="current_operation" direction="out" />
+      <arg type="s" name="new_version" direction="out" />
+      <arg type="x" name="new_size" direction="out" />
+    </method>
+    <method name="RebootIfNeeded">
+    </method>
+    <method name="SetChannel">
+      <arg type="s" name="target_channel" direction="in" />
+      <arg type="b" name="is_powerwash_allowed" direction="in" />
+    </method>
+    <method name="GetChannel">
+      <arg type="b" name="get_current_channel" direction="in" />
+      <arg type="s" name="channel" direction="out" />
+    </method>
+    <method name="SetP2PUpdatePermission">
+      <annotation name="org.freedesktop.DBus.GLib.CSymbol"
+        value="update_engine_service_set_p2p_update_permission" />
+      <annotation name="org.freedesktop.DBus.GLib.ClientCSymbol"
+        value="update_engine_client_set_p2p_update_permission" />
+      <arg type="b" name="enabled" direction="in" />
+    </method>
+    <method name="GetP2PUpdatePermission">
+      <annotation name="org.freedesktop.DBus.GLib.CSymbol"
+        value="update_engine_service_get_p2p_update_permission" />
+      <annotation name="org.freedesktop.DBus.GLib.ClientCSymbol"
+        value="update_engine_client_get_p2p_update_permission" />
+      <arg type="b" name="enabled" direction="out" />
+    </method>
+    <method name="SetUpdateOverCellularPermission">
+      <arg type="b" name="allowed" direction="in" />
+    </method>
+    <method name="GetUpdateOverCellularPermission">
+      <arg type="b" name="allowed" direction="out" />
+    </method>
+    <method name="GetDurationSinceUpdate">
+      <arg type="x" name="usec_wallclock" direction="out" />
+    </method>
+    <signal name="StatusUpdate">
+      <arg type="x" name="last_checked_time" />
+      <arg type="d" name="progress" />
+      <arg type="s" name="current_operation" />
+      <arg type="s" name="new_version" />
+      <arg type="x" name="new_size" />
+    </signal>
+    <method name="GetPrevVersion">
+      <arg type="s" name="prev_version" direction="out" />
+    </method>
+    <method name="GetRollbackPartition">
+      <arg type="s" name="rollback_partition_name" direction="out" />
+    </method>
+  </interface>
+</node>
diff --git a/dbus_service.cc b/dbus_service.cc
new file mode 100644
index 0000000..6ed31d4
--- /dev/null
+++ b/dbus_service.cc
@@ -0,0 +1,342 @@
+//
+// Copyright (C) 2012 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 "update_engine/dbus_service.h"
+
+#include <set>
+#include <string>
+
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/strings/string_utils.h>
+#include <policy/device_policy.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/connection_manager_interface.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/p2p_manager.h"
+#include "update_engine/update_attempter.h"
+
+using base::StringPrintf;
+using brillo::ErrorPtr;
+using brillo::string_utils::ToString;
+using std::set;
+using std::string;
+using update_engine::AttemptUpdateFlags;
+using update_engine::kAttemptUpdateFlagNonInteractive;
+
+namespace {
+// Log and set the error on the passed ErrorPtr.
+void LogAndSetError(ErrorPtr *error,
+                    const tracked_objects::Location& location,
+                    const string& reason) {
+  brillo::Error::AddTo(
+      error, location,
+      brillo::errors::dbus::kDomain,
+      update_engine::kUpdateEngineServiceErrorFailed, reason);
+  LOG(ERROR) << "Sending DBus Failure: " << location.ToString() << ": "
+             << reason;
+}
+}  // namespace
+
+namespace chromeos_update_engine {
+
+UpdateEngineService::UpdateEngineService(SystemState* system_state)
+    : system_state_(system_state) {}
+
+// org::chromium::UpdateEngineInterfaceInterface methods implementation.
+
+bool UpdateEngineService::AttemptUpdate(ErrorPtr* error,
+                                        const string& in_app_version,
+                                        const string& in_omaha_url) {
+  return AttemptUpdateWithFlags(
+      error, in_app_version, in_omaha_url, 0 /* no flags */);
+}
+
+bool UpdateEngineService::AttemptUpdateWithFlags(ErrorPtr* /* error */,
+                                                 const string& in_app_version,
+                                                 const string& in_omaha_url,
+                                                 int32_t in_flags_as_int) {
+  AttemptUpdateFlags flags = static_cast<AttemptUpdateFlags>(in_flags_as_int);
+  bool interactive = !(flags & kAttemptUpdateFlagNonInteractive);
+
+  LOG(INFO) << "Attempt update: app_version=\"" << in_app_version << "\" "
+            << "omaha_url=\"" << in_omaha_url << "\" "
+            << "flags=0x" << std::hex << flags << " "
+            << "interactive=" << (interactive? "yes" : "no");
+  system_state_->update_attempter()->CheckForUpdate(
+      in_app_version, in_omaha_url, interactive);
+  return true;
+}
+
+bool UpdateEngineService::AttemptRollback(ErrorPtr* error,
+                                          bool in_powerwash) {
+  LOG(INFO) << "Attempting rollback to non-active partitions.";
+
+  if (!system_state_->update_attempter()->Rollback(in_powerwash)) {
+    // TODO(dgarrett): Give a more specific error code/reason.
+    LogAndSetError(error, FROM_HERE, "Rollback attempt failed.");
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::CanRollback(ErrorPtr* /* error */,
+                                      bool* out_can_rollback) {
+  bool can_rollback = system_state_->update_attempter()->CanRollback();
+  LOG(INFO) << "Checking to see if we can rollback . Result: " << can_rollback;
+  *out_can_rollback = can_rollback;
+  return true;
+}
+
+bool UpdateEngineService::ResetStatus(ErrorPtr* error) {
+  if (!system_state_->update_attempter()->ResetStatus()) {
+    // TODO(dgarrett): Give a more specific error code/reason.
+    LogAndSetError(error, FROM_HERE, "ResetStatus failed.");
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::GetStatus(ErrorPtr* error,
+                                    int64_t* out_last_checked_time,
+                                    double* out_progress,
+                                    string* out_current_operation,
+                                    string* out_new_version,
+                                    int64_t* out_new_size) {
+  if (!system_state_->update_attempter()->GetStatus(out_last_checked_time,
+                                                    out_progress,
+                                                    out_current_operation,
+                                                    out_new_version,
+                                                    out_new_size)) {
+    LogAndSetError(error, FROM_HERE, "GetStatus failed.");
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::RebootIfNeeded(ErrorPtr* error) {
+  if (!system_state_->update_attempter()->RebootIfNeeded()) {
+    // TODO(dgarrett): Give a more specific error code/reason.
+    LogAndSetError(error, FROM_HERE, "Reboot not needed, or attempt failed.");
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::SetChannel(ErrorPtr* error,
+                                     const string& in_target_channel,
+                                     bool in_is_powerwash_allowed) {
+  const policy::DevicePolicy* device_policy = system_state_->device_policy();
+
+  // The device_policy is loaded in a lazy way before an update check. Load it
+  // now from the libbrillo cache if it wasn't already loaded.
+  if (!device_policy) {
+    UpdateAttempter* update_attempter = system_state_->update_attempter();
+    if (update_attempter) {
+      update_attempter->RefreshDevicePolicy();
+      device_policy = system_state_->device_policy();
+    }
+  }
+
+  bool delegated = false;
+  if (device_policy &&
+      device_policy->GetReleaseChannelDelegated(&delegated) && !delegated) {
+    LogAndSetError(
+        error, FROM_HERE,
+        "Cannot set target channel explicitly when channel "
+        "policy/settings is not delegated");
+    return false;
+  }
+
+  LOG(INFO) << "Setting destination channel to: " << in_target_channel;
+  string error_message;
+  if (!system_state_->request_params()->SetTargetChannel(
+          in_target_channel, in_is_powerwash_allowed, &error_message)) {
+    LogAndSetError(error, FROM_HERE, error_message);
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::GetChannel(ErrorPtr* /* error */,
+                                     bool in_get_current_channel,
+                                     string* out_channel) {
+  OmahaRequestParams* rp = system_state_->request_params();
+  *out_channel = (in_get_current_channel ?
+                  rp->current_channel() : rp->target_channel());
+  return true;
+}
+
+bool UpdateEngineService::SetP2PUpdatePermission(ErrorPtr* error,
+                                                 bool in_enabled) {
+  PrefsInterface* prefs = system_state_->prefs();
+
+  if (!prefs->SetBoolean(kPrefsP2PEnabled, in_enabled)) {
+    LogAndSetError(
+        error, FROM_HERE,
+        StringPrintf("Error setting the update via p2p permission to %s.",
+                     ToString(in_enabled).c_str()));
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::GetP2PUpdatePermission(ErrorPtr* error,
+                                                 bool* out_enabled) {
+  PrefsInterface* prefs = system_state_->prefs();
+
+  bool p2p_pref = false;  // Default if no setting is present.
+  if (prefs->Exists(kPrefsP2PEnabled) &&
+      !prefs->GetBoolean(kPrefsP2PEnabled, &p2p_pref)) {
+    LogAndSetError(error, FROM_HERE, "Error getting the P2PEnabled setting.");
+    return false;
+  }
+
+  *out_enabled = p2p_pref;
+  return true;
+}
+
+bool UpdateEngineService::SetUpdateOverCellularPermission(ErrorPtr* error,
+                                                          bool in_allowed) {
+  set<string> allowed_types;
+  const policy::DevicePolicy* device_policy = system_state_->device_policy();
+
+  // The device_policy is loaded in a lazy way before an update check. Load it
+  // now from the libbrillo cache if it wasn't already loaded.
+  if (!device_policy) {
+    UpdateAttempter* update_attempter = system_state_->update_attempter();
+    if (update_attempter) {
+      update_attempter->RefreshDevicePolicy();
+      device_policy = system_state_->device_policy();
+    }
+  }
+
+  // Check if this setting is allowed by the device policy.
+  if (device_policy &&
+      device_policy->GetAllowedConnectionTypesForUpdate(&allowed_types)) {
+    LogAndSetError(error, FROM_HERE,
+                   "Ignoring the update over cellular setting since there's "
+                   "a device policy enforcing this setting.");
+    return false;
+  }
+
+  // If the policy wasn't loaded yet, then it is still OK to change the local
+  // setting because the policy will be checked again during the update check.
+
+  PrefsInterface* prefs = system_state_->prefs();
+
+  if (!prefs->SetBoolean(kPrefsUpdateOverCellularPermission, in_allowed)) {
+    LogAndSetError(error, FROM_HERE,
+                   string("Error setting the update over cellular to ") +
+                   (in_allowed ? "true" : "false"));
+    return false;
+  }
+  return true;
+}
+
+bool UpdateEngineService::GetUpdateOverCellularPermission(ErrorPtr* /* error */,
+                                                          bool* out_allowed) {
+  ConnectionManagerInterface* cm = system_state_->connection_manager();
+
+  // The device_policy is loaded in a lazy way before an update check and is
+  // used to determine if an update is allowed over cellular. Load the device
+  // policy now from the libbrillo cache if it wasn't already loaded.
+  if (!system_state_->device_policy()) {
+    UpdateAttempter* update_attempter = system_state_->update_attempter();
+    if (update_attempter)
+      update_attempter->RefreshDevicePolicy();
+  }
+
+  // Return the current setting based on the same logic used while checking for
+  // updates. A log message could be printed as the result of this test.
+  LOG(INFO) << "Checking if updates over cellular networks are allowed:";
+  *out_allowed = cm->IsUpdateAllowedOver(
+      chromeos_update_engine::NetworkConnectionType::kCellular,
+      chromeos_update_engine::NetworkTethering::kUnknown);
+  return true;
+}
+
+bool UpdateEngineService::GetDurationSinceUpdate(ErrorPtr* error,
+                                                 int64_t* out_usec_wallclock) {
+  base::Time time;
+  if (!system_state_->update_attempter()->GetBootTimeAtUpdate(&time)) {
+    LogAndSetError(error, FROM_HERE, "No pending update.");
+    return false;
+  }
+
+  ClockInterface* clock = system_state_->clock();
+  *out_usec_wallclock = (clock->GetBootTime() - time).InMicroseconds();
+  return true;
+}
+
+bool UpdateEngineService::GetPrevVersion(ErrorPtr* /* error */,
+                                         string* out_prev_version) {
+  *out_prev_version = system_state_->update_attempter()->GetPrevVersion();
+  return true;
+}
+
+bool UpdateEngineService::GetRollbackPartition(
+    ErrorPtr* /* error */,
+    string* out_rollback_partition_name) {
+  BootControlInterface::Slot rollback_slot =
+      system_state_->update_attempter()->GetRollbackSlot();
+
+  if (rollback_slot == BootControlInterface::kInvalidSlot) {
+    out_rollback_partition_name->clear();
+    return true;
+  }
+
+  string name;
+  if (!system_state_->boot_control()->GetPartitionDevice(
+          "KERNEL", rollback_slot, &name)) {
+    LOG(ERROR) << "Invalid rollback device";
+    return false;
+  }
+
+  LOG(INFO) << "Getting rollback partition name. Result: " << name;
+  *out_rollback_partition_name = name;
+  return true;
+}
+
+UpdateEngineAdaptor::UpdateEngineAdaptor(SystemState* system_state,
+                                         const scoped_refptr<dbus::Bus>& bus)
+    : org::chromium::UpdateEngineInterfaceAdaptor(&dbus_service_),
+    bus_(bus),
+    dbus_service_(system_state),
+    dbus_object_(nullptr,
+                 bus,
+                 dbus::ObjectPath(update_engine::kUpdateEngineServicePath)) {}
+
+void UpdateEngineAdaptor::RegisterAsync(
+    const base::Callback<void(bool)>& completion_callback) {
+  RegisterWithDBusObject(&dbus_object_);
+  dbus_object_.RegisterAsync(completion_callback);
+}
+
+bool UpdateEngineAdaptor::RequestOwnership() {
+  return bus_->RequestOwnershipAndBlock(update_engine::kUpdateEngineServiceName,
+                                        dbus::Bus::REQUIRE_PRIMARY);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/dbus_service.h b/dbus_service.h
new file mode 100644
index 0000000..88bd90a
--- /dev/null
+++ b/dbus_service.h
@@ -0,0 +1,160 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_DBUS_SERVICE_H_
+#define UPDATE_ENGINE_DBUS_SERVICE_H_
+
+#include <inttypes.h>
+
+#include <string>
+
+#include <base/memory/ref_counted.h>
+#include <brillo/errors/error.h>
+
+#include "update_engine/update_attempter.h"
+
+#include "dbus_bindings/org.chromium.UpdateEngineInterface.h"
+
+namespace chromeos_update_engine {
+
+class UpdateEngineService
+    : public org::chromium::UpdateEngineInterfaceInterface {
+ public:
+  explicit UpdateEngineService(SystemState* system_state);
+  virtual ~UpdateEngineService() = default;
+
+  // Implementation of org::chromium::UpdateEngineInterfaceInterface.
+  bool AttemptUpdate(brillo::ErrorPtr* error,
+                     const std::string& in_app_version,
+                     const std::string& in_omaha_url) override;
+
+  bool AttemptUpdateWithFlags(brillo::ErrorPtr* error,
+                              const std::string& in_app_version,
+                              const std::string& in_omaha_url,
+                              int32_t in_flags_as_int) override;
+
+  bool AttemptRollback(brillo::ErrorPtr* error, bool in_powerwash) override;
+
+  // Checks if the system rollback is available by verifying if the secondary
+  // system partition is valid and bootable.
+  bool CanRollback(brillo::ErrorPtr* error, bool* out_can_rollback) override;
+
+  // Resets the status of the update_engine to idle, ignoring any applied
+  // update. This is used for development only.
+  bool ResetStatus(brillo::ErrorPtr* error) override;
+
+  // Returns the current status of the Update Engine. If an update is in
+  // progress, the number of operations, size to download and overall progress
+  // is reported.
+  bool GetStatus(brillo::ErrorPtr* error,
+                 int64_t* out_last_checked_time,
+                 double* out_progress,
+                 std::string* out_current_operation,
+                 std::string* out_new_version,
+                 int64_t* out_new_size) override;
+
+  // Reboots the device if an update is applied and a reboot is required.
+  bool RebootIfNeeded(brillo::ErrorPtr* error) override;
+
+  // Changes the current channel of the device to the target channel. If the
+  // target channel is a less stable channel than the current channel, then the
+  // channel change happens immediately (at the next update check).  If the
+  // target channel is a more stable channel, then if is_powerwash_allowed is
+  // set to true, then also the change happens immediately but with a powerwash
+  // if required. Otherwise, the change takes effect eventually (when the
+  // version on the target channel goes above the version number of what the
+  // device currently has).
+  bool SetChannel(brillo::ErrorPtr* error,
+                  const std::string& in_target_channel,
+                  bool in_is_powerwash_allowed) override;
+
+  // If get_current_channel is set to true, populates |channel| with the name of
+  // the channel that the device is currently on. Otherwise, it populates it
+  // with the name of the channel the device is supposed to be (in case of a
+  // pending channel change).
+  bool GetChannel(brillo::ErrorPtr* error,
+                  bool in_get_current_channel,
+                  std::string* out_channel) override;
+
+  // Enables or disables the sharing and consuming updates over P2P feature
+  // according to the |enabled| argument passed.
+  bool SetP2PUpdatePermission(brillo::ErrorPtr* error,
+                              bool in_enabled) override;
+
+  // Returns the current value for the P2P enabled setting. This involves both
+  // sharing and consuming updates over P2P.
+  bool GetP2PUpdatePermission(brillo::ErrorPtr* error,
+                              bool* out_enabled) override;
+
+  // If there's no device policy installed, sets the update over cellular
+  // networks permission to the |allowed| value. Otherwise, this method returns
+  // with an error since this setting is overridden by the applied policy.
+  bool SetUpdateOverCellularPermission(brillo::ErrorPtr* error,
+                                       bool in_allowed) override;
+
+  // Returns the current value of the update over cellular network setting,
+  // either forced by the device policy if the device is enrolled or the current
+  // user preference otherwise.
+  bool GetUpdateOverCellularPermission(brillo::ErrorPtr* error,
+                                       bool* out_allowed) override;
+
+  // Returns the duration since the last successful update, as the
+  // duration on the wallclock. Returns an error if the device has not
+  // updated.
+  bool GetDurationSinceUpdate(brillo::ErrorPtr* error,
+                              int64_t* out_usec_wallclock) override;
+
+  // Returns the version string of OS that was used before the last reboot
+  // into an updated version. This is available only when rebooting into an
+  // update from previous version, otherwise an empty string is returned.
+  bool GetPrevVersion(brillo::ErrorPtr* error,
+                      std::string* out_prev_version) override;
+
+  // Returns the name of kernel partition that can be rolled back into.
+  bool GetRollbackPartition(brillo::ErrorPtr* error,
+                            std::string* out_rollback_partition_name) override;
+
+ private:
+  SystemState* system_state_;
+};
+
+// The UpdateEngineAdaptor class runs the UpdateEngineInterface in the fixed
+// object path, without an ObjectManager notifying the interfaces, since it is
+// all static and clients don't expect it to be implemented.
+class UpdateEngineAdaptor : public org::chromium::UpdateEngineInterfaceAdaptor {
+ public:
+  UpdateEngineAdaptor(SystemState* system_state,
+                      const scoped_refptr<dbus::Bus>& bus);
+  ~UpdateEngineAdaptor() = default;
+
+  // Register the DBus object with the update engine service asynchronously.
+  // Calls |copmletion_callback| when done passing a boolean indicating if the
+  // registration succeeded.
+  void RegisterAsync(const base::Callback<void(bool)>& completion_callback);
+
+  // Takes ownership of the well-known DBus name and returns whether it
+  // succeeded.
+  bool RequestOwnership();
+
+ private:
+  scoped_refptr<dbus::Bus> bus_;
+  UpdateEngineService dbus_service_;
+  brillo::dbus_utils::DBusObject dbus_object_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_DBUS_SERVICE_H_
diff --git a/dbus_service_unittest.cc b/dbus_service_unittest.cc
new file mode 100644
index 0000000..db63b2d
--- /dev/null
+++ b/dbus_service_unittest.cc
@@ -0,0 +1,143 @@
+//
+// Copyright (C) 2014 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 "update_engine/dbus_service.h"
+
+#include <gtest/gtest.h>
+#include <string>
+
+#include <brillo/errors/error.h>
+#include <policy/libpolicy.h>
+#include <policy/mock_device_policy.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/fake_system_state.h"
+
+using brillo::errors::dbus::kDomain;
+using std::string;
+using testing::Return;
+using testing::SetArgumentPointee;
+using testing::_;
+using update_engine::kUpdateEngineServiceErrorFailed;
+
+namespace chromeos_update_engine {
+
+class UpdateEngineServiceTest : public ::testing::Test {
+ protected:
+  UpdateEngineServiceTest()
+      : mock_update_attempter_(fake_system_state_.mock_update_attempter()),
+        dbus_service_(&fake_system_state_) {}
+
+  void SetUp() override {
+    fake_system_state_.set_device_policy(nullptr);
+  }
+
+  // Fake/mock infrastructure.
+  FakeSystemState fake_system_state_;
+  policy::MockDevicePolicy mock_device_policy_;
+
+  // Shortcut for fake_system_state_.mock_update_attempter().
+  MockUpdateAttempter* mock_update_attempter_;
+
+  brillo::ErrorPtr error_;
+  UpdateEngineService dbus_service_;
+};
+
+TEST_F(UpdateEngineServiceTest, AttemptUpdate) {
+  // Simple test to ensure that the default is an interactive check.
+  EXPECT_CALL(*mock_update_attempter_,
+              CheckForUpdate("app_ver", "url", true /* interactive */));
+  EXPECT_TRUE(dbus_service_.AttemptUpdate(&error_, "app_ver", "url"));
+  EXPECT_EQ(nullptr, error_);
+}
+
+TEST_F(UpdateEngineServiceTest, AttemptUpdateWithFlags) {
+  EXPECT_CALL(*mock_update_attempter_, CheckForUpdate(
+      "app_ver", "url", false /* interactive */));
+  // The update is non-interactive when we pass the non-interactive flag.
+  EXPECT_TRUE(dbus_service_.AttemptUpdateWithFlags(
+      &error_, "app_ver", "url",
+      update_engine::kAttemptUpdateFlagNonInteractive));
+  EXPECT_EQ(nullptr, error_);
+}
+
+// SetChannel is allowed when there's no device policy (the device is not
+// enterprise enrolled).
+TEST_F(UpdateEngineServiceTest, SetChannelWithNoPolicy) {
+  EXPECT_CALL(*mock_update_attempter_, RefreshDevicePolicy());
+  // If SetTargetChannel is called it means the policy check passed.
+  EXPECT_CALL(*fake_system_state_.mock_request_params(),
+              SetTargetChannel("stable-channel", true, _))
+      .WillOnce(Return(true));
+  EXPECT_TRUE(dbus_service_.SetChannel(&error_, "stable-channel", true));
+  ASSERT_EQ(nullptr, error_);
+}
+
+// When the policy is present, the delegated value should be checked.
+TEST_F(UpdateEngineServiceTest, SetChannelWithDelegatedPolicy) {
+  policy::MockDevicePolicy mock_device_policy;
+  fake_system_state_.set_device_policy(&mock_device_policy);
+  EXPECT_CALL(mock_device_policy, GetReleaseChannelDelegated(_))
+      .WillOnce(DoAll(SetArgumentPointee<0>(true), Return(true)));
+  EXPECT_CALL(*fake_system_state_.mock_request_params(),
+              SetTargetChannel("beta-channel", true, _))
+      .WillOnce(Return(true));
+
+  EXPECT_TRUE(dbus_service_.SetChannel(&error_, "beta-channel", true));
+  ASSERT_EQ(nullptr, error_);
+}
+
+// When passing an invalid value (SetTargetChannel fails) an error should be
+// raised.
+TEST_F(UpdateEngineServiceTest, SetChannelWithInvalidChannel) {
+  EXPECT_CALL(*mock_update_attempter_, RefreshDevicePolicy());
+  EXPECT_CALL(*fake_system_state_.mock_request_params(),
+              SetTargetChannel("foo-channel", true, _)).WillOnce(Return(false));
+
+  EXPECT_FALSE(dbus_service_.SetChannel(&error_, "foo-channel", true));
+  ASSERT_NE(nullptr, error_);
+  EXPECT_TRUE(error_->HasError(kDomain, kUpdateEngineServiceErrorFailed));
+}
+
+TEST_F(UpdateEngineServiceTest, GetChannel) {
+  fake_system_state_.mock_request_params()->set_current_channel("current");
+  fake_system_state_.mock_request_params()->set_target_channel("target");
+  string channel;
+  EXPECT_TRUE(dbus_service_.GetChannel(
+      &error_, true /* get_current_channel */, &channel));
+  EXPECT_EQ(nullptr, error_);
+  EXPECT_EQ("current", channel);
+
+  EXPECT_TRUE(dbus_service_.GetChannel(
+      &error_, false /* get_current_channel */, &channel));
+  EXPECT_EQ(nullptr, error_);
+  EXPECT_EQ("target", channel);
+}
+
+TEST_F(UpdateEngineServiceTest, ResetStatusSucceeds) {
+  EXPECT_CALL(*mock_update_attempter_, ResetStatus()).WillOnce(Return(true));
+  EXPECT_TRUE(dbus_service_.ResetStatus(&error_));
+  EXPECT_EQ(nullptr, error_);
+}
+
+TEST_F(UpdateEngineServiceTest, ResetStatusFails) {
+  EXPECT_CALL(*mock_update_attempter_, ResetStatus()).WillOnce(Return(false));
+  EXPECT_FALSE(dbus_service_.ResetStatus(&error_));
+  ASSERT_NE(nullptr, error_);
+  EXPECT_TRUE(error_->HasError(kDomain, kUpdateEngineServiceErrorFailed));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/dbus_test_utils.h b/dbus_test_utils.h
new file mode 100644
index 0000000..b3748ce
--- /dev/null
+++ b/dbus_test_utils.h
@@ -0,0 +1,89 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_DBUS_TEST_UTILS_H_
+#define UPDATE_ENGINE_DBUS_TEST_UTILS_H_
+
+#include <set>
+#include <string>
+
+#include <base/bind.h>
+#include <brillo/message_loops/message_loop.h>
+#include <gmock/gmock.h>
+
+namespace chromeos_update_engine {
+namespace dbus_test_utils {
+
+#define MOCK_SIGNAL_HANDLER_EXPECT_SIGNAL_HANDLER(                           \
+    mock_signal_handler, mock_proxy, signal)                                 \
+  do {                                                                       \
+    EXPECT_CALL((mock_proxy),                                                \
+                Register##signal##SignalHandler(::testing::_, ::testing::_)) \
+        .WillOnce(::chromeos_update_engine::dbus_test_utils::GrabCallbacks(  \
+            &(mock_signal_handler)));                                        \
+  } while (false)
+
+template <typename T>
+class MockSignalHandler {
+ public:
+  MockSignalHandler() = default;
+  ~MockSignalHandler() {
+    if (callback_connected_task_ != brillo::MessageLoop::kTaskIdNull)
+      brillo::MessageLoop::current()->CancelTask(callback_connected_task_);
+  }
+
+  // Returns whether the signal handler is registered.
+  bool IsHandlerRegistered() const { return signal_callback_ != nullptr; }
+
+  const base::Callback<T>& signal_callback() { return *signal_callback_.get(); }
+
+  void GrabCallbacks(
+      const base::Callback<T>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) {
+    signal_callback_.reset(new base::Callback<T>(signal_callback));
+    on_connected_callback_.reset(
+        new dbus::ObjectProxy::OnConnectedCallback(on_connected_callback));
+    // Notify from the main loop that the callback was connected.
+    callback_connected_task_ = brillo::MessageLoop::current()->PostTask(
+        FROM_HERE,
+        base::Bind(&MockSignalHandler<T>::OnCallbackConnected,
+                   base::Unretained(this)));
+  }
+
+ private:
+  void OnCallbackConnected() {
+    callback_connected_task_ = brillo::MessageLoop::kTaskIdNull;
+    on_connected_callback_->Run("", "", true);
+  }
+
+  brillo::MessageLoop::TaskId callback_connected_task_{
+      brillo::MessageLoop::kTaskIdNull};
+
+  std::unique_ptr<base::Callback<T>> signal_callback_;
+  std::unique_ptr<dbus::ObjectProxy::OnConnectedCallback>
+      on_connected_callback_;
+};
+
+// Defines the action that will call MockSignalHandler<T>::GrabCallbacks for the
+// right type.
+ACTION_P(GrabCallbacks, mock_signal_handler) {
+  mock_signal_handler->GrabCallbacks(arg0, arg1);
+}
+
+}  // namespace dbus_test_utils
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_DBUS_TEST_UTILS_H_
diff --git a/fake_file_writer.h b/fake_file_writer.h
new file mode 100644
index 0000000..43b71c7
--- /dev/null
+++ b/fake_file_writer.h
@@ -0,0 +1,76 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_FAKE_FILE_WRITER_H_
+#define UPDATE_ENGINE_FAKE_FILE_WRITER_H_
+
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_consumer/file_writer.h"
+
+// FakeFileWriter is an implementation of FileWriter. It will succeed
+// calls to Open(), Close(), but not do any work. All calls to Write()
+// will append the passed data to an internal vector.
+
+namespace chromeos_update_engine {
+
+class FakeFileWriter : public FileWriter {
+ public:
+  FakeFileWriter() : was_opened_(false), was_closed_(false) {}
+
+  virtual int Open(const char* path, int flags, mode_t mode) {
+    CHECK(!was_opened_);
+    CHECK(!was_closed_);
+    was_opened_ = true;
+    return 0;
+  }
+
+  virtual ssize_t Write(const void* bytes, size_t count) {
+    CHECK(was_opened_);
+    CHECK(!was_closed_);
+    const char* char_bytes = reinterpret_cast<const char*>(bytes);
+    bytes_.insert(bytes_.end(), char_bytes, char_bytes + count);
+    return count;
+  }
+
+  virtual int Close() {
+    CHECK(was_opened_);
+    CHECK(!was_closed_);
+    was_closed_ = true;
+    return 0;
+  }
+
+  const brillo::Blob& bytes() {
+    return bytes_;
+  }
+
+ private:
+  // The internal store of all bytes that have been written
+  brillo::Blob bytes_;
+
+  // These are just to ensure FileWriter methods are called properly.
+  bool was_opened_;
+  bool was_closed_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeFileWriter);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_FAKE_FILE_WRITER_H_
diff --git a/fake_p2p_manager.h b/fake_p2p_manager.h
new file mode 100644
index 0000000..a8cf4ea
--- /dev/null
+++ b/fake_p2p_manager.h
@@ -0,0 +1,130 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_FAKE_P2P_MANAGER_H_
+#define UPDATE_ENGINE_FAKE_P2P_MANAGER_H_
+
+#include <string>
+
+#include "update_engine/p2p_manager.h"
+
+namespace chromeos_update_engine {
+
+// A fake implementation of P2PManager.
+class FakeP2PManager : public P2PManager {
+ public:
+  FakeP2PManager() :
+    is_p2p_enabled_(false),
+    ensure_p2p_running_result_(false),
+    ensure_p2p_not_running_result_(false),
+    perform_housekeeping_result_(false),
+    count_shared_files_result_(0) {}
+
+  // P2PManager overrides.
+  void SetDevicePolicy(const policy::DevicePolicy* device_policy) override {}
+
+  bool IsP2PEnabled() override {
+    return is_p2p_enabled_;
+  }
+
+  bool EnsureP2PRunning() override {
+    return ensure_p2p_running_result_;
+  }
+
+  bool EnsureP2PNotRunning() override {
+    return ensure_p2p_not_running_result_;
+  }
+
+  bool PerformHousekeeping() override {
+    return perform_housekeeping_result_;
+  }
+
+  void LookupUrlForFile(const std::string& file_id,
+                        size_t minimum_size,
+                        base::TimeDelta max_time_to_wait,
+                        LookupCallback callback) override {
+    callback.Run(lookup_url_for_file_result_);
+  }
+
+  bool FileShare(const std::string& file_id,
+                 size_t expected_size) override {
+    return false;
+  }
+
+  base::FilePath FileGetPath(const std::string& file_id) override {
+    return base::FilePath();
+  }
+
+  ssize_t FileGetSize(const std::string& file_id) override {
+    return -1;
+  }
+
+  ssize_t FileGetExpectedSize(const std::string& file_id) override {
+    return -1;
+  }
+
+  bool FileGetVisible(const std::string& file_id,
+                      bool *out_result) override {
+    return false;
+  }
+
+  bool FileMakeVisible(const std::string& file_id) override {
+    return false;
+  }
+
+  int CountSharedFiles() override {
+    return count_shared_files_result_;
+  }
+
+  // Methods for controlling what the fake returns and how it acts.
+  void SetP2PEnabled(bool is_p2p_enabled) {
+    is_p2p_enabled_ = is_p2p_enabled;
+  }
+
+  void SetEnsureP2PRunningResult(bool ensure_p2p_running_result) {
+    ensure_p2p_running_result_ = ensure_p2p_running_result;
+  }
+
+  void SetEnsureP2PNotRunningResult(bool ensure_p2p_not_running_result) {
+    ensure_p2p_not_running_result_ = ensure_p2p_not_running_result;
+  }
+
+  void SetPerformHousekeepingResult(bool perform_housekeeping_result) {
+    perform_housekeeping_result_ = perform_housekeeping_result;
+  }
+
+  void SetCountSharedFilesResult(int count_shared_files_result) {
+    count_shared_files_result_ = count_shared_files_result;
+  }
+
+  void SetLookupUrlForFileResult(const std::string& url) {
+    lookup_url_for_file_result_ = url;
+  }
+
+ private:
+  bool is_p2p_enabled_;
+  bool ensure_p2p_running_result_;
+  bool ensure_p2p_not_running_result_;
+  bool perform_housekeeping_result_;
+  int count_shared_files_result_;
+  std::string lookup_url_for_file_result_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeP2PManager);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_FAKE_P2P_MANAGER_H_
diff --git a/fake_p2p_manager_configuration.h b/fake_p2p_manager_configuration.h
new file mode 100644
index 0000000..3d3afe4
--- /dev/null
+++ b/fake_p2p_manager_configuration.h
@@ -0,0 +1,115 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_FAKE_P2P_MANAGER_CONFIGURATION_H_
+#define UPDATE_ENGINE_FAKE_P2P_MANAGER_CONFIGURATION_H_
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/p2p_manager.h"
+
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+
+namespace chromeos_update_engine {
+
+// Configuration for P2PManager for use in unit tests. Instead of
+// /var/cache/p2p, a temporary directory is used.
+class FakeP2PManagerConfiguration : public P2PManager::Configuration {
+ public:
+  FakeP2PManagerConfiguration() {
+    EXPECT_TRUE(utils::MakeTempDirectory("p2p-tc.XXXXXX", &p2p_dir_));
+  }
+
+  ~FakeP2PManagerConfiguration() {
+    if (p2p_dir_.size() > 0 &&
+        !base::DeleteFile(base::FilePath(p2p_dir_), true)) {
+      PLOG(ERROR) << "Unable to unlink files and directory in " << p2p_dir_;
+    }
+  }
+
+  // P2PManager::Configuration override
+  base::FilePath GetP2PDir() override {
+    return base::FilePath(p2p_dir_);
+  }
+
+  // P2PManager::Configuration override
+  std::vector<std::string> GetInitctlArgs(bool is_start) override {
+    return is_start ? initctl_start_args_ : initctl_stop_args_;
+  }
+
+  // P2PManager::Configuration override
+  std::vector<std::string> GetP2PClientArgs(const std::string &file_id,
+                                            size_t minimum_size) override {
+    std::vector<std::string> formatted_command = p2p_client_cmd_format_;
+    // Replace {variable} on the passed string.
+    std::string str_minimum_size = std::to_string(minimum_size);
+    for (std::string& arg : formatted_command) {
+      ReplaceSubstringsAfterOffset(&arg, 0, "{file_id}", file_id);
+      ReplaceSubstringsAfterOffset(&arg, 0, "{minsize}", str_minimum_size);
+    }
+    return formatted_command;
+  }
+
+  // Use |command_line| instead of "initctl start p2p" when attempting
+  // to start the p2p service.
+  void SetInitctlStartCommand(const std::vector<std::string>& command) {
+    initctl_start_args_ = command;
+  }
+
+  // Use |command_line| instead of "initctl stop p2p" when attempting
+  // to stop the p2p service.
+  void SetInitctlStopCommand(const std::vector<std::string>& command) {
+    initctl_stop_args_ = command;
+  }
+
+  // Use |command_format| instead of "p2p-client --get-url={file_id}
+  // --minimum-size={minsize}" when attempting to look up a file using
+  // p2p-client(1).
+  //
+  // The passed |command_format| argument can have "{file_id}" and "{minsize}"
+  // as substrings of any of its elements, that will be replaced by the
+  // corresponding values passed to GetP2PClientArgs().
+  void SetP2PClientCommand(const std::vector<std::string>& command_format) {
+    p2p_client_cmd_format_ = command_format;
+  }
+
+ private:
+  // The temporary directory used for p2p.
+  std::string p2p_dir_;
+
+  // Argument vector for starting p2p.
+  std::vector<std::string> initctl_start_args_{"initctl", "start", "p2p"};
+
+  // Argument vector for stopping p2p.
+  std::vector<std::string> initctl_stop_args_{"initctl", "stop", "p2p"};
+
+  // A string for generating the p2p-client command. See the
+  // SetP2PClientCommandLine() for details.
+  std::vector<std::string> p2p_client_cmd_format_{
+      "p2p-client", "--get-url={file_id}", "--minimum-size={minsize}"};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeP2PManagerConfiguration);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_FAKE_P2P_MANAGER_CONFIGURATION_H_
diff --git a/fake_shill_proxy.cc b/fake_shill_proxy.cc
new file mode 100644
index 0000000..17698cd
--- /dev/null
+++ b/fake_shill_proxy.cc
@@ -0,0 +1,47 @@
+//
+// Copyright (C) 2015 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 "update_engine/fake_shill_proxy.h"
+
+using org::chromium::flimflam::ManagerProxyMock;
+using org::chromium::flimflam::ServiceProxyInterface;
+
+namespace chromeos_update_engine {
+
+FakeShillProxy::FakeShillProxy()
+    : manager_proxy_mock_(new ManagerProxyMock()) {}
+
+ManagerProxyMock* FakeShillProxy::GetManagerProxy() {
+  return manager_proxy_mock_.get();
+}
+
+std::unique_ptr<ServiceProxyInterface> FakeShillProxy::GetServiceForPath(
+    const dbus::ObjectPath& path) {
+  auto it = service_proxy_mocks_.find(path.value());
+  CHECK(it != service_proxy_mocks_.end()) << "No ServiceProxyMock set for "
+                                          << path.value();
+  std::unique_ptr<ServiceProxyInterface> result = std::move(it->second);
+  service_proxy_mocks_.erase(it);
+  return result;
+}
+
+void FakeShillProxy::SetServiceForPath(
+    const dbus::ObjectPath& path,
+    std::unique_ptr<ServiceProxyInterface> service_proxy) {
+  service_proxy_mocks_[path.value()] = std::move(service_proxy);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/fake_shill_proxy.h b/fake_shill_proxy.h
new file mode 100644
index 0000000..ae17eaa
--- /dev/null
+++ b/fake_shill_proxy.h
@@ -0,0 +1,66 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_FAKE_SHILL_PROXY_H_
+#define UPDATE_ENGINE_FAKE_SHILL_PROXY_H_
+
+#include <map>
+#include <memory>
+#include <string>
+
+#include <base/macros.h>
+#include <shill/dbus-proxies.h>
+#include <shill/dbus-proxy-mocks.h>
+
+#include "update_engine/shill_proxy_interface.h"
+
+namespace chromeos_update_engine {
+
+// This class implements the connection to shill using real DBus calls.
+class FakeShillProxy : public ShillProxyInterface {
+ public:
+  FakeShillProxy();
+  ~FakeShillProxy() override = default;
+
+  // ShillProxyInterface overrides.
+
+  // GetManagerProxy returns the subclass ManagerProxyMock so tests can easily
+  // use it. Mocks for the return value of GetServiceForPath() can be provided
+  // with SetServiceForPath().
+  org::chromium::flimflam::ManagerProxyMock* GetManagerProxy() override;
+  std::unique_ptr<org::chromium::flimflam::ServiceProxyInterface>
+  GetServiceForPath(const dbus::ObjectPath& path) override;
+
+  // Sets the service_proxy that will be returned by GetServiceForPath().
+  void SetServiceForPath(
+      const dbus::ObjectPath& path,
+      std::unique_ptr<org::chromium::flimflam::ServiceProxyInterface>
+          service_proxy);
+
+ private:
+  std::unique_ptr<org::chromium::flimflam::ManagerProxyMock>
+      manager_proxy_mock_;
+
+  std::map<std::string,
+           std::unique_ptr<org::chromium::flimflam::ServiceProxyInterface>>
+      service_proxy_mocks_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeShillProxy);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_FAKE_SHILL_PROXY_H_
diff --git a/fake_system_state.cc b/fake_system_state.cc
new file mode 100644
index 0000000..49ba058
--- /dev/null
+++ b/fake_system_state.cc
@@ -0,0 +1,43 @@
+//
+// Copyright (C) 2012 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 "update_engine/fake_system_state.h"
+
+namespace chromeos_update_engine {
+
+// Mock the SystemStateInterface so that we could lie that
+// OOBE is completed even when there's no such marker file, etc.
+FakeSystemState::FakeSystemState()
+    : mock_update_attempter_(this, nullptr, nullptr, nullptr),
+      mock_request_params_(this),
+      fake_update_manager_(&fake_clock_),
+      clock_(&fake_clock_),
+      connection_manager_(&mock_connection_manager_),
+      hardware_(&fake_hardware_),
+      metrics_lib_(&mock_metrics_lib_),
+      prefs_(&mock_prefs_),
+      powerwash_safe_prefs_(&mock_powerwash_safe_prefs_),
+      payload_state_(&mock_payload_state_),
+      update_attempter_(&mock_update_attempter_),
+      request_params_(&mock_request_params_),
+      p2p_manager_(&mock_p2p_manager_),
+      update_manager_(&fake_update_manager_),
+      device_policy_(nullptr),
+      fake_system_rebooted_(false) {
+  mock_payload_state_.Initialize(this);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/fake_system_state.h b/fake_system_state.h
new file mode 100644
index 0000000..75ef315
--- /dev/null
+++ b/fake_system_state.h
@@ -0,0 +1,274 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_FAKE_SYSTEM_STATE_H_
+#define UPDATE_ENGINE_FAKE_SYSTEM_STATE_H_
+
+#include <base/logging.h>
+#include <gmock/gmock.h>
+#include <policy/mock_device_policy.h>
+#include <power_manager/dbus-proxies.h>
+#include <power_manager/dbus-proxy-mocks.h>
+
+#include "metrics/metrics_library_mock.h"
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/mock_prefs.h"
+#include "update_engine/mock_connection_manager.h"
+#include "update_engine/mock_omaha_request_params.h"
+#include "update_engine/mock_p2p_manager.h"
+#include "update_engine/mock_payload_state.h"
+#include "update_engine/mock_update_attempter.h"
+#include "update_engine/system_state.h"
+#include "update_engine/update_manager/fake_update_manager.h"
+
+namespace chromeos_update_engine {
+
+// Mock the SystemStateInterface so that we could lie that
+// OOBE is completed even when there's no such marker file, etc.
+class FakeSystemState : public SystemState {
+ public:
+  FakeSystemState();
+
+  // Base class overrides. All getters return the current implementation of
+  // various members, either the default (fake/mock) or the one set to override
+  // it by client code.
+
+  BootControlInterface* boot_control() override { return boot_control_; }
+
+  inline ClockInterface* clock() override { return clock_; }
+
+  inline void set_device_policy(
+      const policy::DevicePolicy* device_policy) override {
+    device_policy_ = device_policy;
+  }
+
+  inline const policy::DevicePolicy* device_policy() override {
+    return device_policy_;
+  }
+
+  inline ConnectionManagerInterface* connection_manager() override {
+    return connection_manager_;
+  }
+
+  inline HardwareInterface* hardware() override { return hardware_; }
+
+  inline MetricsLibraryInterface* metrics_lib() override {
+    return metrics_lib_;
+  }
+
+  inline PrefsInterface* prefs() override { return prefs_; }
+
+  inline PrefsInterface* powerwash_safe_prefs() override {
+    return powerwash_safe_prefs_;
+  }
+
+  inline PayloadStateInterface* payload_state() override {
+    return payload_state_;
+  }
+
+  inline UpdateAttempter* update_attempter() override {
+    return update_attempter_;
+  }
+
+  inline OmahaRequestParams* request_params() override {
+    return request_params_;
+  }
+
+  inline P2PManager* p2p_manager() override { return p2p_manager_; }
+
+  inline chromeos_update_manager::UpdateManager* update_manager() override {
+    return update_manager_;
+  }
+
+  inline org::chromium::PowerManagerProxyInterface* power_manager_proxy()
+      override {
+    return power_manager_proxy_;
+  }
+
+  inline bool system_rebooted() override { return fake_system_rebooted_; }
+
+  // Setters for the various members, can be used for overriding the default
+  // implementations. For convenience, setting to a null pointer will restore
+  // the default implementation.
+
+  void set_boot_control(BootControlInterface* boot_control) {
+    boot_control_ = boot_control ? boot_control : &fake_boot_control_;
+  }
+
+  inline void set_clock(ClockInterface* clock) {
+    clock_ = clock ? clock : &fake_clock_;
+  }
+
+  inline void set_connection_manager(
+      ConnectionManagerInterface* connection_manager) {
+    connection_manager_ = (connection_manager ? connection_manager :
+                           &mock_connection_manager_);
+  }
+
+  inline void set_hardware(HardwareInterface* hardware) {
+    hardware_ = hardware ? hardware : &fake_hardware_;
+  }
+
+  inline void set_metrics_lib(MetricsLibraryInterface* metrics_lib) {
+    metrics_lib_ = metrics_lib ? metrics_lib : &mock_metrics_lib_;
+  }
+
+  inline void set_prefs(PrefsInterface* prefs) {
+    prefs_ = prefs ? prefs : &mock_prefs_;
+  }
+
+  inline void set_powerwash_safe_prefs(PrefsInterface* powerwash_safe_prefs) {
+    powerwash_safe_prefs_ = (powerwash_safe_prefs ? powerwash_safe_prefs :
+                             &mock_powerwash_safe_prefs_);
+  }
+
+  inline void set_payload_state(PayloadStateInterface *payload_state) {
+    payload_state_ = payload_state ? payload_state : &mock_payload_state_;
+  }
+
+  inline void set_update_attempter(UpdateAttempter* update_attempter) {
+    update_attempter_ = (update_attempter ? update_attempter :
+                         &mock_update_attempter_);
+  }
+
+  inline void set_request_params(OmahaRequestParams* request_params) {
+    request_params_ = (request_params ? request_params :
+                       &mock_request_params_);
+  }
+
+  inline void set_p2p_manager(P2PManager *p2p_manager) {
+    p2p_manager_ = p2p_manager ? p2p_manager : &mock_p2p_manager_;
+  }
+
+  inline void set_update_manager(
+      chromeos_update_manager::UpdateManager *update_manager) {
+    update_manager_ = update_manager ? update_manager : &fake_update_manager_;
+  }
+
+  inline void set_system_rebooted(bool system_rebooted) {
+    fake_system_rebooted_ = system_rebooted;
+  }
+
+  // Getters for the built-in default implementations. These return the actual
+  // concrete type of each implementation. For additional safety, they will fail
+  // whenever the requested default was overridden by a different
+  // implementation.
+
+  inline FakeBootControl* fake_boot_control() {
+    CHECK(boot_control_ == &fake_boot_control_);
+    return &fake_boot_control_;
+  }
+
+  inline FakeClock* fake_clock() {
+    CHECK(clock_ == &fake_clock_);
+    return &fake_clock_;
+  }
+
+  inline testing::NiceMock<MockConnectionManager>* mock_connection_manager() {
+    CHECK(connection_manager_ == &mock_connection_manager_);
+    return &mock_connection_manager_;
+  }
+
+  inline FakeHardware* fake_hardware() {
+    CHECK(hardware_ == &fake_hardware_);
+    return &fake_hardware_;
+  }
+
+  inline testing::NiceMock<MetricsLibraryMock>* mock_metrics_lib() {
+    CHECK(metrics_lib_ == &mock_metrics_lib_);
+    return &mock_metrics_lib_;
+  }
+
+  inline testing::NiceMock<MockPrefs> *mock_prefs() {
+    CHECK(prefs_ == &mock_prefs_);
+    return &mock_prefs_;
+  }
+
+  inline testing::NiceMock<MockPrefs> *mock_powerwash_safe_prefs() {
+    CHECK(powerwash_safe_prefs_ == &mock_powerwash_safe_prefs_);
+    return &mock_powerwash_safe_prefs_;
+  }
+
+  inline testing::NiceMock<MockPayloadState>* mock_payload_state() {
+    CHECK(payload_state_ == &mock_payload_state_);
+    return &mock_payload_state_;
+  }
+
+  inline testing::NiceMock<MockUpdateAttempter>* mock_update_attempter() {
+    CHECK(update_attempter_ == &mock_update_attempter_);
+    return &mock_update_attempter_;
+  }
+
+  inline testing::NiceMock<MockOmahaRequestParams>* mock_request_params() {
+    CHECK(request_params_ == &mock_request_params_);
+    return &mock_request_params_;
+  }
+
+  inline testing::NiceMock<MockP2PManager>* mock_p2p_manager() {
+    CHECK(p2p_manager_ == &mock_p2p_manager_);
+    return &mock_p2p_manager_;
+  }
+
+  inline chromeos_update_manager::FakeUpdateManager* fake_update_manager() {
+    CHECK(update_manager_ == &fake_update_manager_);
+    return &fake_update_manager_;
+  }
+
+ private:
+  // Default mock/fake implementations (owned).
+  FakeBootControl fake_boot_control_;
+  FakeClock fake_clock_;
+  testing::NiceMock<MockConnectionManager> mock_connection_manager_;
+  FakeHardware fake_hardware_;
+  testing::NiceMock<MetricsLibraryMock> mock_metrics_lib_;
+  testing::NiceMock<MockPrefs> mock_prefs_;
+  testing::NiceMock<MockPrefs> mock_powerwash_safe_prefs_;
+  testing::NiceMock<MockPayloadState> mock_payload_state_;
+  testing::NiceMock<MockUpdateAttempter> mock_update_attempter_;
+  testing::NiceMock<MockOmahaRequestParams> mock_request_params_;
+  testing::NiceMock<MockP2PManager> mock_p2p_manager_;
+  chromeos_update_manager::FakeUpdateManager fake_update_manager_;
+  org::chromium::PowerManagerProxyMock mock_power_manager_;
+
+  // Pointers to objects that client code can override. They are initialized to
+  // the default implementations above.
+  BootControlInterface* boot_control_{&fake_boot_control_};
+  ClockInterface* clock_;
+  ConnectionManagerInterface* connection_manager_;
+  HardwareInterface* hardware_;
+  MetricsLibraryInterface* metrics_lib_;
+  PrefsInterface* prefs_;
+  PrefsInterface* powerwash_safe_prefs_;
+  PayloadStateInterface* payload_state_;
+  UpdateAttempter* update_attempter_;
+  OmahaRequestParams* request_params_;
+  P2PManager* p2p_manager_;
+  chromeos_update_manager::UpdateManager* update_manager_;
+  org::chromium::PowerManagerProxyInterface* power_manager_proxy_{
+      &mock_power_manager_};
+
+  // Other object pointers (not preinitialized).
+  const policy::DevicePolicy* device_policy_;
+
+  // Other data members.
+  bool fake_system_rebooted_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_FAKE_SYSTEM_STATE_H_
diff --git a/generate_pc_file.sh b/generate_pc_file.sh
new file mode 100755
index 0000000..ab101f4
--- /dev/null
+++ b/generate_pc_file.sh
@@ -0,0 +1,30 @@
+#!/bin/bash
+
+#
+# Copyright (C) 2015 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.
+#
+
+set -e
+
+OUT=$1
+shift
+PC_IN=$1
+shift
+INCLUDE_DIR=$1
+shift
+
+sed \
+  -e "s|@INCLUDE_DIR@|${INCLUDE_DIR}|g" \
+  "${PC_IN}.pc.in" > "${OUT}/${PC_IN}.pc"
diff --git a/hardware_android.cc b/hardware_android.cc
new file mode 100644
index 0000000..a20fe6f
--- /dev/null
+++ b/hardware_android.cc
@@ -0,0 +1,113 @@
+//
+// Copyright (C) 2015 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 "update_engine/hardware_android.h"
+
+#include <base/files/file_util.h>
+#include <brillo/make_unique_ptr.h>
+#include <cutils/properties.h>
+
+#include "update_engine/common/hardware.h"
+#include "update_engine/common/platform_constants.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace hardware {
+
+// Factory defined in hardware.h.
+std::unique_ptr<HardwareInterface> CreateHardware() {
+  return brillo::make_unique_ptr(new HardwareAndroid());
+}
+
+}  // namespace hardware
+
+// In Android there are normally three kinds of builds: eng, userdebug and user.
+// These builds target respectively a developer build, a debuggable version of
+// the final product and the pristine final product the end user will run.
+// Apart from the ro.build.type property name, they differ in the following
+// properties that characterize the builds:
+// * eng builds: ro.secure=0 and ro.debuggable=1
+// * userdebug builds: ro.secure=1 and ro.debuggable=1
+// * user builds: ro.secure=1 and ro.debuggable=0
+//
+// See IsOfficialBuild() and IsNormalMode() for the meaning of these options in
+// Android.
+
+bool HardwareAndroid::IsOfficialBuild() const {
+  // We run an official build iff ro.secure == 1, because we expect the build to
+  // behave like the end user product and check for updates. Note that while
+  // developers are able to build "official builds" by just running "make user",
+  // that will only result in a more restrictive environment. The important part
+  // is that we don't produce and push "non-official" builds to the end user.
+  //
+  // In case of a non-bool value, we take the most restrictive option and
+  // assume we are in an official-build.
+  return property_get_bool("ro.secure", 1) != 0;
+}
+
+bool HardwareAndroid::IsNormalBootMode() const {
+  // We are running in "dev-mode" iff ro.debuggable == 1. In dev-mode the
+  // update_engine will allow extra developers options, such as providing a
+  // different update URL. In case of error, we assume the build is in
+  // normal-mode.
+  return property_get_bool("ro.debuggable", 0) != 1;
+}
+
+bool HardwareAndroid::IsOOBEComplete(base::Time* out_time_of_oobe) const {
+  LOG(WARNING) << "STUB: Assuming OOBE is complete.";
+  if (out_time_of_oobe)
+    *out_time_of_oobe = base::Time();
+  return true;
+}
+
+string HardwareAndroid::GetHardwareClass() const {
+  LOG(WARNING) << "STUB: GetHardwareClass().";
+  return "ANDROID";
+}
+
+string HardwareAndroid::GetFirmwareVersion() const {
+  LOG(WARNING) << "STUB: GetFirmwareVersion().";
+  return "0";
+}
+
+string HardwareAndroid::GetECVersion() const {
+  LOG(WARNING) << "STUB: GetECVersion().";
+  return "0";
+}
+
+int HardwareAndroid::GetPowerwashCount() const {
+  LOG(WARNING) << "STUB: Assuming no factory reset was performed.";
+  return 0;
+}
+
+bool HardwareAndroid::GetNonVolatileDirectory(base::FilePath* path) const {
+  base::FilePath local_path(constants::kNonVolatileDirectory);
+  if (!base::PathExists(local_path)) {
+    LOG(ERROR) << "Non-volatile directory not found: " << local_path.value();
+    return false;
+  }
+  *path = local_path;
+  return true;
+}
+
+bool HardwareAndroid::GetPowerwashSafeDirectory(base::FilePath* path) const {
+  // On Android, we don't have a directory persisted across powerwash.
+  return false;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/hardware_android.h b/hardware_android.h
new file mode 100644
index 0000000..1b03661
--- /dev/null
+++ b/hardware_android.h
@@ -0,0 +1,53 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_HARDWARE_ANDROID_H_
+#define UPDATE_ENGINE_HARDWARE_ANDROID_H_
+
+#include <string>
+
+#include <base/macros.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/hardware.h"
+#include "update_engine/common/hardware_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements the real interface with the hardware in the Android platform.
+class HardwareAndroid final : public HardwareInterface {
+ public:
+  HardwareAndroid() = default;
+  ~HardwareAndroid() override = default;
+
+  // HardwareInterface methods.
+  bool IsOfficialBuild() const override;
+  bool IsNormalBootMode() const override;
+  bool IsOOBEComplete(base::Time* out_time_of_oobe) const override;
+  std::string GetHardwareClass() const override;
+  std::string GetFirmwareVersion() const override;
+  std::string GetECVersion() const override;
+  int GetPowerwashCount() const override;
+  bool GetNonVolatileDirectory(base::FilePath* path) const override;
+  bool GetPowerwashSafeDirectory(base::FilePath* path) const override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(HardwareAndroid);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_HARDWARE_ANDROID_H_
diff --git a/hardware_chromeos.cc b/hardware_chromeos.cc
new file mode 100644
index 0000000..ccb3978
--- /dev/null
+++ b/hardware_chromeos.cc
@@ -0,0 +1,153 @@
+//
+// Copyright (C) 2013 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 "update_engine/hardware_chromeos.h"
+
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <brillo/make_unique_ptr.h>
+#include <vboot/crossystem.h>
+
+extern "C" {
+#include "vboot/vboot_host.h"
+}
+
+#include "update_engine/common/hardware.h"
+#include "update_engine/common/hwid_override.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace {
+
+const char kOOBECompletedMarker[] = "/home/chronos/.oobe_completed";
+
+// The stateful directory used by update_engine to store powerwash-safe files.
+// The files stored here must be whitelisted in the powerwash scripts.
+const char kPowerwashSafeDirectory[] =
+    "/mnt/stateful_partition/unencrypted/preserve";
+
+// The powerwash_count marker file contains the number of times the device was
+// powerwashed. This value is incremented by the clobber-state script when
+// a powerwash is performed.
+const char kPowerwashCountMarker[] = "powerwash_count";
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+namespace hardware {
+
+// Factory defined in hardware.h.
+std::unique_ptr<HardwareInterface> CreateHardware() {
+  return brillo::make_unique_ptr(new HardwareChromeOS());
+}
+
+}  // namespace hardware
+
+bool HardwareChromeOS::IsOfficialBuild() const {
+  return VbGetSystemPropertyInt("debug_build") == 0;
+}
+
+bool HardwareChromeOS::IsNormalBootMode() const {
+  bool dev_mode = VbGetSystemPropertyInt("devsw_boot") != 0;
+  return !dev_mode;
+}
+
+bool HardwareChromeOS::IsOOBEComplete(base::Time* out_time_of_oobe) const {
+  struct stat statbuf;
+  if (stat(kOOBECompletedMarker, &statbuf) != 0) {
+    if (errno != ENOENT) {
+      PLOG(ERROR) << "Error getting information about "
+                  << kOOBECompletedMarker;
+    }
+    return false;
+  }
+
+  if (out_time_of_oobe != nullptr)
+    *out_time_of_oobe = base::Time::FromTimeT(statbuf.st_mtime);
+  return true;
+}
+
+static string ReadValueFromCrosSystem(const string& key) {
+  char value_buffer[VB_MAX_STRING_PROPERTY];
+
+  const char* rv = VbGetSystemPropertyString(key.c_str(), value_buffer,
+                                             sizeof(value_buffer));
+  if (rv != nullptr) {
+    string return_value(value_buffer);
+    base::TrimWhitespaceASCII(return_value, base::TRIM_ALL, &return_value);
+    return return_value;
+  }
+
+  LOG(ERROR) << "Unable to read crossystem key " << key;
+  return "";
+}
+
+string HardwareChromeOS::GetHardwareClass() const {
+  if (USE_HWID_OVERRIDE) {
+    return HwidOverride::Read(base::FilePath("/"));
+  }
+  return ReadValueFromCrosSystem("hwid");
+}
+
+string HardwareChromeOS::GetFirmwareVersion() const {
+  return ReadValueFromCrosSystem("fwid");
+}
+
+string HardwareChromeOS::GetECVersion() const {
+  string input_line;
+  int exit_code = 0;
+  vector<string> cmd = {"/usr/sbin/mosys", "-k", "ec", "info"};
+
+  bool success = Subprocess::SynchronousExec(cmd, &exit_code, &input_line);
+  if (!success || exit_code) {
+    LOG(ERROR) << "Unable to read ec info from mosys (" << exit_code << ")";
+    return "";
+  }
+
+  return utils::ParseECVersion(input_line);
+}
+
+int HardwareChromeOS::GetPowerwashCount() const {
+  int powerwash_count;
+  base::FilePath marker_path = base::FilePath(kPowerwashSafeDirectory).Append(
+      kPowerwashCountMarker);
+  string contents;
+  if (!utils::ReadFile(marker_path.value(), &contents))
+    return -1;
+  base::TrimWhitespaceASCII(contents, base::TRIM_TRAILING, &contents);
+  if (!base::StringToInt(contents, &powerwash_count))
+    return -1;
+  return powerwash_count;
+}
+
+bool HardwareChromeOS::GetNonVolatileDirectory(base::FilePath* path) const {
+  *path = base::FilePath(constants::kNonVolatileDirectory);
+  return true;
+}
+
+bool HardwareChromeOS::GetPowerwashSafeDirectory(base::FilePath* path) const {
+  *path = base::FilePath(kPowerwashSafeDirectory);
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/hardware_chromeos.h b/hardware_chromeos.h
new file mode 100644
index 0000000..80888ab
--- /dev/null
+++ b/hardware_chromeos.h
@@ -0,0 +1,54 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_HARDWARE_CHROMEOS_H_
+#define UPDATE_ENGINE_HARDWARE_CHROMEOS_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/hardware_interface.h"
+
+namespace chromeos_update_engine {
+
+// Implements the real interface with Chrome OS verified boot and recovery
+// process.
+class HardwareChromeOS final : public HardwareInterface {
+ public:
+  HardwareChromeOS() = default;
+  ~HardwareChromeOS() override = default;
+
+  // HardwareInterface methods.
+  bool IsOfficialBuild() const override;
+  bool IsNormalBootMode() const override;
+  bool IsOOBEComplete(base::Time* out_time_of_oobe) const override;
+  std::string GetHardwareClass() const override;
+  std::string GetFirmwareVersion() const override;
+  std::string GetECVersion() const override;
+  int GetPowerwashCount() const override;
+  bool GetNonVolatileDirectory(base::FilePath* path) const override;
+  bool GetPowerwashSafeDirectory(base::FilePath* path) const override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(HardwareChromeOS);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_HARDWARE_CHROMEOS_H_
diff --git a/image_properties.h b/image_properties.h
new file mode 100644
index 0000000..6026c2e
--- /dev/null
+++ b/image_properties.h
@@ -0,0 +1,84 @@
+//
+// Copyright (C) 2015 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.
+//
+
+// This module abstracts the properties tied to the current running image. These
+// properties are meant to be constant during the life of this daemon, but can
+// be modified in dev-move or non-official builds.
+
+#ifndef UPDATE_ENGINE_IMAGE_PROPERTIES_H_
+#define UPDATE_ENGINE_IMAGE_PROPERTIES_H_
+
+#include <string>
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+// The read-only system properties of the running image.
+struct ImageProperties {
+  // The product id of the image used for all channels, except canary.
+  std::string product_id;
+  // The canary-channel product id.
+  std::string canary_product_id;
+
+  // The product version of this image.
+  std::string version;
+
+  // The board name this image was built for.
+  std::string board;
+
+  // The release channel this image was obtained from.
+  std::string current_channel;
+
+  // The Omaha URL this image should get updates from.
+  std::string omaha_url;
+};
+
+// The mutable image properties are read-write image properties, initialized
+// with values from the image but can be modified by storing them in the
+// stateful partition.
+struct MutableImageProperties {
+  // The release channel we are tracking.
+  std::string target_channel;
+
+  // Whether powerwash is allowed when downloading an update for the selected
+  // target_channel.
+  bool is_powerwash_allowed{false};
+};
+
+// Loads all the image properties from the running system. In case of error
+// loading any of these properties from the read-only system image a default
+// value may be returned instead.
+ImageProperties LoadImageProperties(SystemState* system_state);
+
+// Loads the mutable image properties from the stateful partition if found or the
+// system image otherwise.
+MutableImageProperties LoadMutableImageProperties(SystemState* system_state);
+
+// Stores the mutable image properties in the stateful partition. Returns
+// whether the operation succeeded.
+bool StoreMutableImageProperties(SystemState* system_state,
+                                 const MutableImageProperties& properties);
+
+// Sets the root_prefix used to load files from during unittests to
+// |test_root_prefix|. Passing a nullptr value resets it to the default.
+namespace test {
+void SetImagePropertiesRootPrefix(const char* test_root_prefix);
+}  // namespace test
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_IMAGE_PROPERTIES_H_
diff --git a/image_properties_android.cc b/image_properties_android.cc
new file mode 100644
index 0000000..00822da
--- /dev/null
+++ b/image_properties_android.cc
@@ -0,0 +1,111 @@
+//
+// Copyright (C) 2015 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 "update_engine/image_properties.h"
+
+#include <string>
+
+#include <base/logging.h>
+#include <brillo/osrelease_reader.h>
+
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/system_state.h"
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// Build time properties name used in Brillo.
+const char kProductId[] = "product_id";
+const char kProductVersion[] = "product_version";
+
+// Prefs used to store the target channel and powerwash settings.
+const char kPrefsImgPropChannelName[] = "img-prop-channel-name";
+const char kPrefsImgPropPowerwashAllowed[] = "img-prop-powerwash-allowed";
+
+std::string GetStringWithDefault(const brillo::OsReleaseReader& osrelease,
+                                 const std::string& key,
+                                 const std::string& default_value) {
+  std::string result;
+  if (osrelease.GetString(key, &result))
+    return result;
+  LOG(INFO) << "Cannot load ImageProperty " << key << ", using default value "
+            << default_value;
+  return default_value;
+}
+
+}  // namespace
+
+namespace test {
+void SetImagePropertiesRootPrefix(const char* /* test_root_prefix */) {}
+}  // namespace test
+
+ImageProperties LoadImageProperties(SystemState* system_state) {
+  ImageProperties result;
+
+  brillo::OsReleaseReader osrelease;
+  osrelease.Load();
+  result.product_id = GetStringWithDefault(
+      osrelease, kProductId, "developer-boards:brillo-starter-board");
+  result.canary_product_id = result.product_id;
+  result.version = GetStringWithDefault(osrelease, kProductVersion, "0.0.0.0");
+
+  result.board = "brillo";
+
+  // Brillo images don't have a channel assigned. We stored the name of the
+  // channel where we got the image from in prefs at the time of the update, so
+  // we use that as the current channel if available. During provisioning, there
+  // is no value assigned, so we default to the "stable-channel".
+  std::string current_channel_key =
+      kPrefsChannelOnSlotPrefix +
+      std::to_string(system_state->boot_control()->GetCurrentSlot());
+  std::string current_channel;
+  if (!system_state->prefs()->Exists(current_channel_key) ||
+      !system_state->prefs()->GetString(current_channel_key, &current_channel))
+    current_channel = "stable-channel";
+  result.current_channel = current_channel;
+
+  // Brillo only supports the official omaha URL.
+  result.omaha_url = constants::kOmahaDefaultProductionURL;
+
+  return result;
+}
+
+MutableImageProperties LoadMutableImageProperties(SystemState* system_state) {
+  MutableImageProperties result;
+  PrefsInterface* const prefs = system_state->prefs();
+  if (!prefs->GetString(kPrefsImgPropChannelName, &result.target_channel))
+    result.target_channel.clear();
+  if (!prefs->GetBoolean(kPrefsImgPropPowerwashAllowed,
+                         &result.is_powerwash_allowed)) {
+    result.is_powerwash_allowed = false;
+  }
+  return result;
+}
+
+bool StoreMutableImageProperties(SystemState* system_state,
+                                 const MutableImageProperties& properties) {
+  PrefsInterface* const prefs = system_state->prefs();
+  return (
+      prefs->SetString(kPrefsImgPropChannelName, properties.target_channel) &&
+      prefs->SetBoolean(kPrefsImgPropPowerwashAllowed,
+                        properties.is_powerwash_allowed));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/image_properties_chromeos.cc b/image_properties_chromeos.cc
new file mode 100644
index 0000000..501e662
--- /dev/null
+++ b/image_properties_chromeos.cc
@@ -0,0 +1,150 @@
+//
+// Copyright (C) 2015 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 "update_engine/image_properties.h"
+
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <brillo/key_value_store.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/system_state.h"
+
+namespace {
+
+const char kLsbRelease[] = "/etc/lsb-release";
+
+const char kLsbReleaseAppIdKey[] = "CHROMEOS_RELEASE_APPID";
+const char kLsbReleaseAutoUpdateServerKey[] = "CHROMEOS_AUSERVER";
+const char kLsbReleaseBoardAppIdKey[] = "CHROMEOS_BOARD_APPID";
+const char kLsbReleaseBoardKey[] = "CHROMEOS_RELEASE_BOARD";
+const char kLsbReleaseCanaryAppIdKey[] = "CHROMEOS_CANARY_APPID";
+const char kLsbReleaseIsPowerwashAllowedKey[] = "CHROMEOS_IS_POWERWASH_ALLOWED";
+const char kLsbReleaseUpdateChannelKey[] = "CHROMEOS_RELEASE_TRACK";
+const char kLsbReleaseVersionKey[] = "CHROMEOS_RELEASE_VERSION";
+
+const char kDefaultAppId[] = "{87efface-864d-49a5-9bb3-4b050a7c227a}";
+
+// A prefix added to the path, used for testing.
+const char* root_prefix = nullptr;
+
+std::string GetStringWithDefault(const brillo::KeyValueStore& store,
+                                 const std::string& key,
+                                 const std::string& default_value) {
+  std::string result;
+  if (store.GetString(key, &result))
+    return result;
+  LOG(INFO) << "Cannot load ImageProperty " << key << ", using default value "
+            << default_value;
+  return default_value;
+}
+
+enum class LsbReleaseSource {
+  kSystem,
+  kStateful,
+};
+
+// Loads the lsb-release properties into the key-value |store| reading the file
+// from either the system image or the stateful partition as specified by
+// |source|. The loaded values are added to the store, possibly overriding
+// existing values.
+void LoadLsbRelease(LsbReleaseSource source, brillo::KeyValueStore* store) {
+  std::string path;
+  if (root_prefix)
+    path = root_prefix;
+  if (source == LsbReleaseSource::kStateful)
+    path += chromeos_update_engine::kStatefulPartition;
+  store->Load(base::FilePath(path + kLsbRelease));
+}
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+namespace test {
+void SetImagePropertiesRootPrefix(const char* test_root_prefix) {
+  root_prefix = test_root_prefix;
+}
+}  // namespace test
+
+ImageProperties LoadImageProperties(SystemState* system_state) {
+  ImageProperties result;
+
+  brillo::KeyValueStore lsb_release;
+  LoadLsbRelease(LsbReleaseSource::kSystem, &lsb_release);
+  result.current_channel = GetStringWithDefault(
+      lsb_release, kLsbReleaseUpdateChannelKey, "stable-channel");
+
+  // In dev-mode and unofficial build we can override the image properties set
+  // in the system image with the ones from the stateful partition, except the
+  // channel of the current image.
+  HardwareInterface* const hardware = system_state->hardware();
+  if (!hardware->IsOfficialBuild() || !hardware->IsNormalBootMode())
+    LoadLsbRelease(LsbReleaseSource::kStateful, &lsb_release);
+
+  // The release_app_id is used as the default appid, but can be override by
+  // the board appid in the general case or the canary appid for the canary
+  // channel only.
+  std::string release_app_id =
+      GetStringWithDefault(lsb_release, kLsbReleaseAppIdKey, kDefaultAppId);
+
+  result.product_id = GetStringWithDefault(
+      lsb_release, kLsbReleaseBoardAppIdKey, release_app_id);
+  result.canary_product_id = GetStringWithDefault(
+      lsb_release, kLsbReleaseCanaryAppIdKey, release_app_id);
+  result.board = GetStringWithDefault(lsb_release, kLsbReleaseBoardKey, "");
+  result.version = GetStringWithDefault(lsb_release, kLsbReleaseVersionKey, "");
+  result.omaha_url =
+      GetStringWithDefault(lsb_release, kLsbReleaseAutoUpdateServerKey,
+                           constants::kOmahaDefaultProductionURL);
+
+  return result;
+}
+
+MutableImageProperties LoadMutableImageProperties(SystemState* system_state) {
+  MutableImageProperties result;
+  brillo::KeyValueStore lsb_release;
+  LoadLsbRelease(LsbReleaseSource::kSystem, &lsb_release);
+  LoadLsbRelease(LsbReleaseSource::kStateful, &lsb_release);
+  result.target_channel = GetStringWithDefault(
+      lsb_release, kLsbReleaseUpdateChannelKey, "stable-channel");
+  if (!lsb_release.GetBoolean(kLsbReleaseIsPowerwashAllowedKey,
+                              &result.is_powerwash_allowed))
+    result.is_powerwash_allowed = false;
+  return result;
+}
+
+bool StoreMutableImageProperties(SystemState* system_state,
+                                 const MutableImageProperties& properties) {
+  brillo::KeyValueStore lsb_release;
+  LoadLsbRelease(LsbReleaseSource::kStateful, &lsb_release);
+  lsb_release.SetString(kLsbReleaseUpdateChannelKey, properties.target_channel);
+  lsb_release.SetBoolean(kLsbReleaseIsPowerwashAllowedKey,
+                         properties.is_powerwash_allowed);
+
+  std::string root_prefix_str = root_prefix ? root_prefix : "";
+  base::FilePath path(root_prefix_str + kStatefulPartition + kLsbRelease);
+  if (!base::DirectoryExists(path.DirName()))
+    base::CreateDirectory(path.DirName());
+  return lsb_release.Save(path);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/include/debugd/dbus-constants.h b/include/debugd/dbus-constants.h
new file mode 100644
index 0000000..3427a99
--- /dev/null
+++ b/include/debugd/dbus-constants.h
@@ -0,0 +1,56 @@
+// Copyright 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef SYSTEM_API_DBUS_DEBUGD_DBUS_CONSTANTS_H_
+#define SYSTEM_API_DBUS_DEBUGD_DBUS_CONSTANTS_H_
+
+namespace debugd {
+const char kDebugdInterface[] = "org.chromium.debugd";
+const char kDebugdServicePath[] = "/org/chromium/debugd";
+const char kDebugdServiceName[] = "org.chromium.debugd";
+
+// Methods.
+const char kDumpDebugLogs[] = "DumpDebugLogs";
+const char kGetDebugLogs[] = "GetDebugLogs";
+const char kGetInterfaces[] = "GetInterfaces";
+const char kGetModemStatus[] = "GetModemStatus";
+const char kGetNetworkStatus[] = "GetNetworkStatus";
+const char kGetPerfOutput[] = "GetPerfOutput";
+const char kGetRandomPerfOutput[] = "GetRandomPerfOutput";
+const char kGetRichPerfData[] = "GetRichPerfData";
+const char kGetRoutes[] = "GetRoutes";
+const char kGetWiMaxStatus[] = "GetWiMaxStatus";
+const char kSetDebugMode[] = "SetDebugMode";
+const char kSystraceStart[] = "SystraceStart";
+const char kSystraceStop[] = "SystraceStop";
+const char kSystraceStatus[] = "SystraceStatus";
+const char kGetLog[] = "GetLog";
+const char kGetAllLogs[] = "GetAllLogs";
+const char kGetUserLogFiles[] = "GetUserLogFiles";
+const char kGetFeedbackLogs[] = "GetFeedbackLogs";
+const char kTestICMP[] = "TestICMP";
+const char kTestICMPWithOptions[] = "TestICMPWithOptions";
+const char kLogKernelTaskStates[] = "LogKernelTaskStates";
+const char kUploadCrashes[] = "UploadCrashes";
+const char kRemoveRootfsVerification[] = "RemoveRootfsVerification";
+const char kEnableChromeRemoteDebugging[] = "EnableChromeRemoteDebugging";
+const char kEnableBootFromUsb[] = "EnableBootFromUsb";
+const char kConfigureSshServer[] = "ConfigureSshServer";
+const char kSetUserPassword[] = "SetUserPassword";
+const char kEnableChromeDevFeatures[] = "EnableChromeDevFeatures";
+const char kQueryDevFeatures[] = "QueryDevFeatures";
+
+// Values.
+enum DevFeatureFlag {
+  DEV_FEATURES_DISABLED = 1 << 0,
+  DEV_FEATURE_ROOTFS_VERIFICATION_REMOVED = 1 << 1,
+  DEV_FEATURE_BOOT_FROM_USB_ENABLED = 1 << 2,
+  DEV_FEATURE_SSH_SERVER_CONFIGURED = 1 << 3,
+  DEV_FEATURE_DEV_MODE_ROOT_PASSWORD_SET = 1 << 4,
+  DEV_FEATURE_SYSTEM_ROOT_PASSWORD_SET = 1 << 5,
+  DEV_FEATURE_CHROME_REMOTE_DEBUGGING_ENABLED = 1 << 6,
+};
+}  // namespace debugd
+
+#endif  // SYSTEM_API_DBUS_DEBUGD_DBUS_CONSTANTS_H_
diff --git a/include/debugd/dbus-proxies.h b/include/debugd/dbus-proxies.h
new file mode 100644
index 0000000..a528480
--- /dev/null
+++ b/include/debugd/dbus-proxies.h
@@ -0,0 +1,2334 @@
+// Automatic generation of D-Bus interfaces:
+//  - org.chromium.debugd
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXIES_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXIES_H
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <base/memory/ref_counted.h>
+#include <brillo/any.h>
+#include <brillo/dbus/dbus_method_invoker.h>
+#include <brillo/dbus/dbus_property.h>
+#include <brillo/dbus/dbus_signal_handler.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <dbus/bus.h>
+#include <dbus/message.h>
+#include <dbus/object_manager.h>
+#include <dbus/object_path.h>
+#include <dbus/object_proxy.h>
+
+namespace org {
+namespace chromium {
+
+// Abstract interface proxy for org::chromium::debugd.
+class debugdProxyInterface {
+ public:
+  virtual ~debugdProxyInterface() = default;
+
+  // Starts pinging the specified hostname with the specified options, with
+  // output directed to the given output file descriptor. The returned opaque
+  // string functions as a handle for this particular ping. Multiple pings
+  // can be running at once.
+  virtual bool PingStart(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts pinging the specified hostname with the specified options, with
+  // output directed to the given output file descriptor. The returned opaque
+  // string functions as a handle for this particular ping. Multiple pings
+  // can be running at once.
+  virtual void PingStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running ping.
+  virtual bool PingStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running ping.
+  virtual void PingStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Start system/kernel tracing.  If tracing is already enabled it is
+  // stopped first and any collected events are discarded.  The kernel
+  // must have been configured to support tracing.
+  virtual bool SystraceStart(
+      const std::string& in_categories,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Start system/kernel tracing.  If tracing is already enabled it is
+  // stopped first and any collected events are discarded.  The kernel
+  // must have been configured to support tracing.
+  virtual void SystraceStartAsync(
+      const std::string& in_categories,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stop system/kernel tracing and write the collected event data.
+  virtual bool SystraceStop(
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stop system/kernel tracing and write the collected event data.
+  virtual void SystraceStopAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Return current status for system/kernel tracing including whether it
+  // is enabled, the tracing clock, and the set of events enabled.
+  virtual bool SystraceStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Return current status for system/kernel tracing including whether it
+  // is enabled, the tracing clock, and the set of events enabled.
+  virtual void SystraceStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool TracePathStart(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void TracePathStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running tracepath.
+  virtual bool TracePathStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running tracepath.
+  virtual void TracePathStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns the routing table.
+  virtual bool GetRoutes(
+      const brillo::VariantDictionary& in_options,
+      std::vector<std::string>* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns the routing table.
+  virtual void GetRoutesAsync(
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::vector<std::string>& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns modem information as a JSON string. See the design document for
+  // a rationale.
+  virtual bool GetModemStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns modem information as a JSON string. See the design document for
+  // a rationale.
+  virtual void GetModemStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs the specified command through the modem serial interface and
+  // returns the output.
+  virtual bool RunModemCommand(
+      const std::string& in_command,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs the specified command through the modem serial interface and
+  // returns the output.
+  virtual void RunModemCommandAsync(
+      const std::string& in_command,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns network information as a JSON string. See the design document
+  // for a rationale.
+  virtual bool GetNetworkStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns network information as a JSON string. See the design document
+  // for a rationale.
+  virtual void GetNetworkStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns WiMAX information as a JSON string. See the design document for
+  // a rationale.
+  virtual bool GetWiMaxStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns WiMAX information as a JSON string. See the design document for
+  // a rationale.
+  virtual void GetWiMaxStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs system-wide perf profiling. The profile parameters are selected by
+  // perf_args.
+  virtual bool GetPerfOutput(
+      uint32_t in_duration_sec,
+      const std::vector<std::string>& in_perf_args,
+      int32_t* out_status,
+      std::vector<uint8_t>* out_perf_data,
+      std::vector<uint8_t>* out_perf_stat,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs system-wide perf profiling. The profile parameters are selected by
+  // perf_args.
+  virtual void GetPerfOutputAsync(
+      uint32_t in_duration_sec,
+      const std::vector<std::string>& in_perf_args,
+      const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs system-wide perf profiling. It can can profile events other than
+  // cycles (example: iTLB-misses), and can collect branch profiles. It can
+  // also return raw counter values. The exact profile or counters to be
+  // collected is chosen at random and depends on what CPU is used by the
+  // system (certain CPUs do not support certain profiling modes).
+  virtual bool GetRandomPerfOutput(
+      uint32_t in_duration_sec,
+      int32_t* out_status,
+      std::vector<uint8_t>* out_perf_data,
+      std::vector<uint8_t>* out_perf_stat,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs system-wide perf profiling. It can can profile events other than
+  // cycles (example: iTLB-misses), and can collect branch profiles. It can
+  // also return raw counter values. The exact profile or counters to be
+  // collected is chosen at random and depends on what CPU is used by the
+  // system (certain CPUs do not support certain profiling modes).
+  virtual void GetRandomPerfOutputAsync(
+      uint32_t in_duration_sec,
+      const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns perf event data. Does systemwide profiling. It can profile
+  // events other than cycles (example: iTLB-misses), and can collect branch
+  // profiles. The exact profile to be collected is chosen at random
+  // and depends on what CPU is used by the system (certain CPUs do not
+  // support certain profiling modes).
+  virtual bool GetRichPerfData(
+      uint32_t in_duration_sec,
+      std::vector<uint8_t>* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns perf event data. Does systemwide profiling. It can profile
+  // events other than cycles (example: iTLB-misses), and can collect branch
+  // profiles. The exact profile to be collected is chosen at random
+  // and depends on what CPU is used by the system (certain CPUs do not
+  // support certain profiling modes).
+  virtual void GetRichPerfDataAsync(
+      uint32_t in_duration_sec,
+      const base::Callback<void(const std::vector<uint8_t>& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // DEPRECATED: Use DumpDebugLogs instead.
+  // Packages up system logs into a .tar.gz and returns it over the supplied
+  // file descriptor.
+  virtual bool GetDebugLogs(
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // DEPRECATED: Use DumpDebugLogs instead.
+  // Packages up system logs into a .tar.gz and returns it over the supplied
+  // file descriptor.
+  virtual void GetDebugLogsAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Packages up system logs into a .tar(.gz) and returns it over the
+  // supplied file descriptor.
+  virtual bool DumpDebugLogs(
+      bool in_is_compressed,
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Packages up system logs into a .tar(.gz) and returns it over the
+  // supplied file descriptor.
+  virtual void DumpDebugLogsAsync(
+      bool in_is_compressed,
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Enables or disables debug mode for a specified subsystem.
+  virtual bool SetDebugMode(
+      const std::string& in_subsystem,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Enables or disables debug mode for a specified subsystem.
+  virtual void SetDebugModeAsync(
+      const std::string& in_subsystem,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Fetches the contents of a single system log, identified by name. See
+  // /src/log_tool.cc for a list of valid names.
+  virtual bool GetLog(
+      const std::string& in_log,
+      std::string* out_contents,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Fetches the contents of a single system log, identified by name. See
+  // /src/log_tool.cc for a list of valid names.
+  virtual void GetLogAsync(
+      const std::string& in_log,
+      const base::Callback<void(const std::string& /*contents*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns all the system logs.
+  virtual bool GetAllLogs(
+      std::map<std::string, std::string>* out_logs,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns all the system logs.
+  virtual void GetAllLogsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns system logs for feedback reports.
+  virtual bool GetFeedbackLogs(
+      std::map<std::string, std::string>* out_logs,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns system logs for feedback reports.
+  virtual void GetFeedbackLogsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns list of User log file names that Chrome itself must collect.
+  // These logfiles are relative to the user's profile path and must be
+  // collected separately for each user.
+  virtual bool GetUserLogFiles(
+      std::map<std::string, std::string>* out_user_log_files,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns list of User log file names that Chrome itself must collect.
+  // These logfiles are relative to the user's profile path and must be
+  // collected separately for each user.
+  virtual void GetUserLogFilesAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*user_log_files*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Example method. See /doc/hacking.md.
+  virtual bool GetExample(
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Example method. See /doc/hacking.md.
+  virtual void GetExampleAsync(
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns information about network interfaces as a JSON string.
+  virtual bool GetInterfaces(
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Returns information about network interfaces as a JSON string.
+  virtual void GetInterfacesAsync(
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Tests ICMP connectivity to a specified host.
+  virtual bool TestICMP(
+      const std::string& in_host,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Tests ICMP connectivity to a specified host.
+  virtual void TestICMPAsync(
+      const std::string& in_host,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Tests ICMP connectivity to a specified host (with options).
+  virtual bool TestICMPWithOptions(
+      const std::string& in_host,
+      const std::map<std::string, std::string>& in_options,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Tests ICMP connectivity to a specified host (with options).
+  virtual void TestICMPWithOptionsAsync(
+      const std::string& in_host,
+      const std::map<std::string, std::string>& in_options,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs BatteryFirmware utility.
+  virtual bool BatteryFirmware(
+      const std::string& in_option,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs BatteryFirmware utility.
+  virtual void BatteryFirmwareAsync(
+      const std::string& in_option,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs Smartctl utility.
+  virtual bool Smartctl(
+      const std::string& in_option,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Runs Smartctl utility.
+  virtual void SmartctlAsync(
+      const std::string& in_option,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts running memtester.
+  virtual bool MemtesterStart(
+      const dbus::FileDescriptor& in_outfd,
+      uint32_t in_memory,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts running memtester.
+  virtual void MemtesterStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      uint32_t in_memory,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops running memtester.
+  virtual bool MemtesterStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops running memtester.
+  virtual void MemtesterStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts running badblocks test.
+  virtual bool BadblocksStart(
+      const dbus::FileDescriptor& in_outfd,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts running badblocks test.
+  virtual void BadblocksStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops running badblocks.
+  virtual bool BadblocksStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops running badblocks.
+  virtual void BadblocksStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts a packet capture with the specified options, with diagnostic
+  // status directed to the "statfd" file descriptor and packet capture
+  // data sent to the "outfd" file descriptor.  The returned opaque string
+  // functions as a handle for this particular packet capture.  Multiple
+  // captures can be running at once.  Captures can be initiated on
+  // Ethernet-like devices or WiFi devices in "client mode" (showing only
+  // Ethernet frames) by specifying the "device" parameter (see below).
+  // By specifying a channel, the script will find or create a "monitor
+  // mode" interface if one is available and produce an "over the air"
+  // packet capture.  The name of the output packet capture file is sent
+  // to the output file descriptor.
+  virtual bool PacketCaptureStart(
+      const dbus::FileDescriptor& in_statfd,
+      const dbus::FileDescriptor& in_outfd,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Starts a packet capture with the specified options, with diagnostic
+  // status directed to the "statfd" file descriptor and packet capture
+  // data sent to the "outfd" file descriptor.  The returned opaque string
+  // functions as a handle for this particular packet capture.  Multiple
+  // captures can be running at once.  Captures can be initiated on
+  // Ethernet-like devices or WiFi devices in "client mode" (showing only
+  // Ethernet frames) by specifying the "device" parameter (see below).
+  // By specifying a channel, the script will find or create a "monitor
+  // mode" interface if one is available and produce an "over the air"
+  // packet capture.  The name of the output packet capture file is sent
+  // to the output file descriptor.
+  virtual void PacketCaptureStartAsync(
+      const dbus::FileDescriptor& in_statfd,
+      const dbus::FileDescriptor& in_outfd,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running packet capture.
+  virtual bool PacketCaptureStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Stops a running packet capture.
+  virtual void PacketCaptureStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Triggers show-task-states(T) SysRq.
+  // See https://www.kernel.org/doc/Documentation/sysrq.txt.
+  virtual bool LogKernelTaskStates(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Triggers show-task-states(T) SysRq.
+  // See https://www.kernel.org/doc/Documentation/sysrq.txt.
+  virtual void LogKernelTaskStatesAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Triggers uploading of system crashes (the crash_sender program).
+  virtual bool UploadCrashes(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Triggers uploading of system crashes (the crash_sender program).
+  virtual void UploadCrashesAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Removes rootfs verification. Requires a system reboot before it will
+  // take effect. Restricted to pre-owner dev mode.
+  virtual bool RemoveRootfsVerification(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Removes rootfs verification. Requires a system reboot before it will
+  // take effect. Restricted to pre-owner dev mode.
+  virtual void RemoveRootfsVerificationAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Enables OS booting from a USB image. Restricted to pre-owner dev mode.
+  virtual bool EnableBootFromUsb(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Enables OS booting from a USB image. Restricted to pre-owner dev mode.
+  virtual void EnableBootFromUsbAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets up sshd to provide an SSH server immediately and on future reboots.
+  // Also installs the test SSH keys to allow access by cros tools. Requires
+  // that rootfs verification has been removed. Restricted to pre-owner dev
+  // mode.
+  virtual bool ConfigureSshServer(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets up sshd to provide an SSH server immediately and on future reboots.
+  // Also installs the test SSH keys to allow access by cros tools. Requires
+  // that rootfs verification has been removed. Restricted to pre-owner dev
+  // mode.
+  virtual void ConfigureSshServerAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets both the system and dev mode password for the indicated account.
+  // Restricted to pre-owner dev mode.
+  virtual bool SetUserPassword(
+      const std::string& in_username,
+      const std::string& in_password,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets both the system and dev mode password for the indicated account.
+  // Restricted to pre-owner dev mode.
+  virtual void SetUserPasswordAsync(
+      const std::string& in_username,
+      const std::string& in_password,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets up Chrome for remote debugging. It will take effect after a reboot
+  // and using port 9222.
+  // Requires that rootfs verification has been removed. Restricted to
+  // pre-owner dev mode.
+  virtual bool EnableChromeRemoteDebugging(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Sets up Chrome for remote debugging. It will take effect after a reboot
+  // and using port 9222.
+  // Requires that rootfs verification has been removed. Restricted to
+  // pre-owner dev mode.
+  virtual void EnableChromeRemoteDebuggingAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Convenience function to enable a predefined set of tools from the Chrome
+  // UI. Equivalent to calling these functions in order:
+  //   1. EnableBootFromUsb()
+  //   2. ConfigureSshServer()
+  //   3. SetUserPassword("root", root_password)
+  // Requires that rootfs verification has been removed. If any sub-function
+  // fails, this function will exit with an error without attempting any
+  // further configuration or rollback. Restricted to pre-owner dev mode.
+  virtual bool EnableChromeDevFeatures(
+      const std::string& in_root_password,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Convenience function to enable a predefined set of tools from the Chrome
+  // UI. Equivalent to calling these functions in order:
+  //   1. EnableBootFromUsb()
+  //   2. ConfigureSshServer()
+  //   3. SetUserPassword("root", root_password)
+  // Requires that rootfs verification has been removed. If any sub-function
+  // fails, this function will exit with an error without attempting any
+  // further configuration or rollback. Restricted to pre-owner dev mode.
+  virtual void EnableChromeDevFeaturesAsync(
+      const std::string& in_root_password,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Queries which dev features have been enabled. Each dev feature will be
+  // indicated by a bit flag in the return value. Flags are defined in the
+  // DevFeatureFlag enumeration. If the dev tools are unavailable (system is
+  // not in dev mode/pre-login state), the DEV_FEATURES_DISABLED flag will be
+  // set and the rest of the bits will always be set to 0.
+  virtual bool QueryDevFeatures(
+      int32_t* out_features,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Queries which dev features have been enabled. Each dev feature will be
+  // indicated by a bit flag in the return value. Flags are defined in the
+  // DevFeatureFlag enumeration. If the dev tools are unavailable (system is
+  // not in dev mode/pre-login state), the DEV_FEATURES_DISABLED flag will be
+  // set and the rest of the bits will always be set to 0.
+  virtual void QueryDevFeaturesAsync(
+      const base::Callback<void(int32_t /*features*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Allow uploading of device coredump files.
+  virtual bool EnableDevCoredumpUpload(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Allow uploading of device coredump files.
+  virtual void EnableDevCoredumpUploadAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Disallow uploading of device coredump files.
+  virtual bool DisableDevCoredumpUpload(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // Disallow uploading of device coredump files.
+  virtual void DisableDevCoredumpUploadAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+};
+
+}  // namespace chromium
+}  // namespace org
+
+namespace org {
+namespace chromium {
+
+// Interface proxy for org::chromium::debugd.
+class debugdProxy final : public debugdProxyInterface {
+ public:
+  debugdProxy(const scoped_refptr<dbus::Bus>& bus) :
+      bus_{bus},
+      dbus_object_proxy_{
+          bus_->GetObjectProxy(service_name_, object_path_)} {
+  }
+
+  ~debugdProxy() override {
+    bus_->RemoveObjectProxy(
+        service_name_, object_path_, base::Bind(&base::DoNothing));
+  }
+
+  void ReleaseObjectProxy(const base::Closure& callback) {
+    bus_->RemoveObjectProxy(service_name_, object_path_, callback);
+  }
+
+  const dbus::ObjectPath& GetObjectPath() const {
+    return object_path_;
+  }
+
+  dbus::ObjectProxy* GetObjectProxy() const { return dbus_object_proxy_; }
+
+  // Starts pinging the specified hostname with the specified options, with
+  // output directed to the given output file descriptor. The returned opaque
+  // string functions as a handle for this particular ping. Multiple pings
+  // can be running at once.
+  bool PingStart(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PingStart",
+        error,
+        in_outfd,
+        in_destination,
+        in_options);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_handle);
+  }
+
+  // Starts pinging the specified hostname with the specified options, with
+  // output directed to the given output file descriptor. The returned opaque
+  // string functions as a handle for this particular ping. Multiple pings
+  // can be running at once.
+  void PingStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PingStart",
+        success_callback,
+        error_callback,
+        in_outfd,
+        in_destination,
+        in_options);
+  }
+
+  // Stops a running ping.
+  bool PingStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PingStop",
+        error,
+        in_handle);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stops a running ping.
+  void PingStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PingStop",
+        success_callback,
+        error_callback,
+        in_handle);
+  }
+
+  // Start system/kernel tracing.  If tracing is already enabled it is
+  // stopped first and any collected events are discarded.  The kernel
+  // must have been configured to support tracing.
+  bool SystraceStart(
+      const std::string& in_categories,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStart",
+        error,
+        in_categories);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Start system/kernel tracing.  If tracing is already enabled it is
+  // stopped first and any collected events are discarded.  The kernel
+  // must have been configured to support tracing.
+  void SystraceStartAsync(
+      const std::string& in_categories,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStart",
+        success_callback,
+        error_callback,
+        in_categories);
+  }
+
+  // Stop system/kernel tracing and write the collected event data.
+  bool SystraceStop(
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStop",
+        error,
+        in_outfd);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stop system/kernel tracing and write the collected event data.
+  void SystraceStopAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStop",
+        success_callback,
+        error_callback,
+        in_outfd);
+  }
+
+  // Return current status for system/kernel tracing including whether it
+  // is enabled, the tracing clock, and the set of events enabled.
+  bool SystraceStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStatus",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Return current status for system/kernel tracing including whether it
+  // is enabled, the tracing clock, and the set of events enabled.
+  void SystraceStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SystraceStatus",
+        success_callback,
+        error_callback);
+  }
+
+  bool TracePathStart(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TracePathStart",
+        error,
+        in_outfd,
+        in_destination,
+        in_options);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_handle);
+  }
+
+  void TracePathStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const std::string& in_destination,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TracePathStart",
+        success_callback,
+        error_callback,
+        in_outfd,
+        in_destination,
+        in_options);
+  }
+
+  // Stops a running tracepath.
+  bool TracePathStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TracePathStop",
+        error,
+        in_handle);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stops a running tracepath.
+  void TracePathStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TracePathStop",
+        success_callback,
+        error_callback,
+        in_handle);
+  }
+
+  // Returns the routing table.
+  bool GetRoutes(
+      const brillo::VariantDictionary& in_options,
+      std::vector<std::string>* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRoutes",
+        error,
+        in_options);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Returns the routing table.
+  void GetRoutesAsync(
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::vector<std::string>& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRoutes",
+        success_callback,
+        error_callback,
+        in_options);
+  }
+
+  // Returns modem information as a JSON string. See the design document for
+  // a rationale.
+  bool GetModemStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetModemStatus",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Returns modem information as a JSON string. See the design document for
+  // a rationale.
+  void GetModemStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetModemStatus",
+        success_callback,
+        error_callback);
+  }
+
+  // Runs the specified command through the modem serial interface and
+  // returns the output.
+  bool RunModemCommand(
+      const std::string& in_command,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "RunModemCommand",
+        error,
+        in_command);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Runs the specified command through the modem serial interface and
+  // returns the output.
+  void RunModemCommandAsync(
+      const std::string& in_command,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "RunModemCommand",
+        success_callback,
+        error_callback,
+        in_command);
+  }
+
+  // Returns network information as a JSON string. See the design document
+  // for a rationale.
+  bool GetNetworkStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetNetworkStatus",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Returns network information as a JSON string. See the design document
+  // for a rationale.
+  void GetNetworkStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetNetworkStatus",
+        success_callback,
+        error_callback);
+  }
+
+  // Returns WiMAX information as a JSON string. See the design document for
+  // a rationale.
+  bool GetWiMaxStatus(
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetWiMaxStatus",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Returns WiMAX information as a JSON string. See the design document for
+  // a rationale.
+  void GetWiMaxStatusAsync(
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetWiMaxStatus",
+        success_callback,
+        error_callback);
+  }
+
+  // Runs system-wide perf profiling. The profile parameters are selected by
+  // perf_args.
+  bool GetPerfOutput(
+      uint32_t in_duration_sec,
+      const std::vector<std::string>& in_perf_args,
+      int32_t* out_status,
+      std::vector<uint8_t>* out_perf_data,
+      std::vector<uint8_t>* out_perf_stat,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetPerfOutput",
+        error,
+        in_duration_sec,
+        in_perf_args);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status, out_perf_data, out_perf_stat);
+  }
+
+  // Runs system-wide perf profiling. The profile parameters are selected by
+  // perf_args.
+  void GetPerfOutputAsync(
+      uint32_t in_duration_sec,
+      const std::vector<std::string>& in_perf_args,
+      const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetPerfOutput",
+        success_callback,
+        error_callback,
+        in_duration_sec,
+        in_perf_args);
+  }
+
+  // Runs system-wide perf profiling. It can can profile events other than
+  // cycles (example: iTLB-misses), and can collect branch profiles. It can
+  // also return raw counter values. The exact profile or counters to be
+  // collected is chosen at random and depends on what CPU is used by the
+  // system (certain CPUs do not support certain profiling modes).
+  bool GetRandomPerfOutput(
+      uint32_t in_duration_sec,
+      int32_t* out_status,
+      std::vector<uint8_t>* out_perf_data,
+      std::vector<uint8_t>* out_perf_stat,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRandomPerfOutput",
+        error,
+        in_duration_sec);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status, out_perf_data, out_perf_stat);
+  }
+
+  // Runs system-wide perf profiling. It can can profile events other than
+  // cycles (example: iTLB-misses), and can collect branch profiles. It can
+  // also return raw counter values. The exact profile or counters to be
+  // collected is chosen at random and depends on what CPU is used by the
+  // system (certain CPUs do not support certain profiling modes).
+  void GetRandomPerfOutputAsync(
+      uint32_t in_duration_sec,
+      const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRandomPerfOutput",
+        success_callback,
+        error_callback,
+        in_duration_sec);
+  }
+
+  // Returns perf event data. Does systemwide profiling. It can profile
+  // events other than cycles (example: iTLB-misses), and can collect branch
+  // profiles. The exact profile to be collected is chosen at random
+  // and depends on what CPU is used by the system (certain CPUs do not
+  // support certain profiling modes).
+  bool GetRichPerfData(
+      uint32_t in_duration_sec,
+      std::vector<uint8_t>* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRichPerfData",
+        error,
+        in_duration_sec);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Returns perf event data. Does systemwide profiling. It can profile
+  // events other than cycles (example: iTLB-misses), and can collect branch
+  // profiles. The exact profile to be collected is chosen at random
+  // and depends on what CPU is used by the system (certain CPUs do not
+  // support certain profiling modes).
+  void GetRichPerfDataAsync(
+      uint32_t in_duration_sec,
+      const base::Callback<void(const std::vector<uint8_t>& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetRichPerfData",
+        success_callback,
+        error_callback,
+        in_duration_sec);
+  }
+
+  // DEPRECATED: Use DumpDebugLogs instead.
+  // Packages up system logs into a .tar.gz and returns it over the supplied
+  // file descriptor.
+  bool GetDebugLogs(
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetDebugLogs",
+        error,
+        in_outfd);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // DEPRECATED: Use DumpDebugLogs instead.
+  // Packages up system logs into a .tar.gz and returns it over the supplied
+  // file descriptor.
+  void GetDebugLogsAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetDebugLogs",
+        success_callback,
+        error_callback,
+        in_outfd);
+  }
+
+  // Packages up system logs into a .tar(.gz) and returns it over the
+  // supplied file descriptor.
+  bool DumpDebugLogs(
+      bool in_is_compressed,
+      const dbus::FileDescriptor& in_outfd,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "DumpDebugLogs",
+        error,
+        in_is_compressed,
+        in_outfd);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Packages up system logs into a .tar(.gz) and returns it over the
+  // supplied file descriptor.
+  void DumpDebugLogsAsync(
+      bool in_is_compressed,
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "DumpDebugLogs",
+        success_callback,
+        error_callback,
+        in_is_compressed,
+        in_outfd);
+  }
+
+  // Enables or disables debug mode for a specified subsystem.
+  bool SetDebugMode(
+      const std::string& in_subsystem,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SetDebugMode",
+        error,
+        in_subsystem);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Enables or disables debug mode for a specified subsystem.
+  void SetDebugModeAsync(
+      const std::string& in_subsystem,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SetDebugMode",
+        success_callback,
+        error_callback,
+        in_subsystem);
+  }
+
+  // Fetches the contents of a single system log, identified by name. See
+  // /src/log_tool.cc for a list of valid names.
+  bool GetLog(
+      const std::string& in_log,
+      std::string* out_contents,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetLog",
+        error,
+        in_log);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_contents);
+  }
+
+  // Fetches the contents of a single system log, identified by name. See
+  // /src/log_tool.cc for a list of valid names.
+  void GetLogAsync(
+      const std::string& in_log,
+      const base::Callback<void(const std::string& /*contents*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetLog",
+        success_callback,
+        error_callback,
+        in_log);
+  }
+
+  // Returns all the system logs.
+  bool GetAllLogs(
+      std::map<std::string, std::string>* out_logs,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetAllLogs",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_logs);
+  }
+
+  // Returns all the system logs.
+  void GetAllLogsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetAllLogs",
+        success_callback,
+        error_callback);
+  }
+
+  // Returns system logs for feedback reports.
+  bool GetFeedbackLogs(
+      std::map<std::string, std::string>* out_logs,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetFeedbackLogs",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_logs);
+  }
+
+  // Returns system logs for feedback reports.
+  void GetFeedbackLogsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetFeedbackLogs",
+        success_callback,
+        error_callback);
+  }
+
+  // Returns list of User log file names that Chrome itself must collect.
+  // These logfiles are relative to the user's profile path and must be
+  // collected separately for each user.
+  bool GetUserLogFiles(
+      std::map<std::string, std::string>* out_user_log_files,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetUserLogFiles",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_user_log_files);
+  }
+
+  // Returns list of User log file names that Chrome itself must collect.
+  // These logfiles are relative to the user's profile path and must be
+  // collected separately for each user.
+  void GetUserLogFilesAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*user_log_files*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetUserLogFiles",
+        success_callback,
+        error_callback);
+  }
+
+  // Example method. See /doc/hacking.md.
+  bool GetExample(
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetExample",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Example method. See /doc/hacking.md.
+  void GetExampleAsync(
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetExample",
+        success_callback,
+        error_callback);
+  }
+
+  // Returns information about network interfaces as a JSON string.
+  bool GetInterfaces(
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetInterfaces",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Returns information about network interfaces as a JSON string.
+  void GetInterfacesAsync(
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "GetInterfaces",
+        success_callback,
+        error_callback);
+  }
+
+  // Tests ICMP connectivity to a specified host.
+  bool TestICMP(
+      const std::string& in_host,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TestICMP",
+        error,
+        in_host);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Tests ICMP connectivity to a specified host.
+  void TestICMPAsync(
+      const std::string& in_host,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TestICMP",
+        success_callback,
+        error_callback,
+        in_host);
+  }
+
+  // Tests ICMP connectivity to a specified host (with options).
+  bool TestICMPWithOptions(
+      const std::string& in_host,
+      const std::map<std::string, std::string>& in_options,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TestICMPWithOptions",
+        error,
+        in_host,
+        in_options);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Tests ICMP connectivity to a specified host (with options).
+  void TestICMPWithOptionsAsync(
+      const std::string& in_host,
+      const std::map<std::string, std::string>& in_options,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "TestICMPWithOptions",
+        success_callback,
+        error_callback,
+        in_host,
+        in_options);
+  }
+
+  // Runs BatteryFirmware utility.
+  bool BatteryFirmware(
+      const std::string& in_option,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BatteryFirmware",
+        error,
+        in_option);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Runs BatteryFirmware utility.
+  void BatteryFirmwareAsync(
+      const std::string& in_option,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BatteryFirmware",
+        success_callback,
+        error_callback,
+        in_option);
+  }
+
+  // Runs Smartctl utility.
+  bool Smartctl(
+      const std::string& in_option,
+      std::string* out_result,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "Smartctl",
+        error,
+        in_option);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_result);
+  }
+
+  // Runs Smartctl utility.
+  void SmartctlAsync(
+      const std::string& in_option,
+      const base::Callback<void(const std::string& /*result*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "Smartctl",
+        success_callback,
+        error_callback,
+        in_option);
+  }
+
+  // Starts running memtester.
+  bool MemtesterStart(
+      const dbus::FileDescriptor& in_outfd,
+      uint32_t in_memory,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "MemtesterStart",
+        error,
+        in_outfd,
+        in_memory);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Starts running memtester.
+  void MemtesterStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      uint32_t in_memory,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "MemtesterStart",
+        success_callback,
+        error_callback,
+        in_outfd,
+        in_memory);
+  }
+
+  // Stops running memtester.
+  bool MemtesterStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "MemtesterStop",
+        error,
+        in_handle);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stops running memtester.
+  void MemtesterStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "MemtesterStop",
+        success_callback,
+        error_callback,
+        in_handle);
+  }
+
+  // Starts running badblocks test.
+  bool BadblocksStart(
+      const dbus::FileDescriptor& in_outfd,
+      std::string* out_status,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BadblocksStart",
+        error,
+        in_outfd);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_status);
+  }
+
+  // Starts running badblocks test.
+  void BadblocksStartAsync(
+      const dbus::FileDescriptor& in_outfd,
+      const base::Callback<void(const std::string& /*status*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BadblocksStart",
+        success_callback,
+        error_callback,
+        in_outfd);
+  }
+
+  // Stops running badblocks.
+  bool BadblocksStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BadblocksStop",
+        error,
+        in_handle);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stops running badblocks.
+  void BadblocksStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "BadblocksStop",
+        success_callback,
+        error_callback,
+        in_handle);
+  }
+
+  // Starts a packet capture with the specified options, with diagnostic
+  // status directed to the "statfd" file descriptor and packet capture
+  // data sent to the "outfd" file descriptor.  The returned opaque string
+  // functions as a handle for this particular packet capture.  Multiple
+  // captures can be running at once.  Captures can be initiated on
+  // Ethernet-like devices or WiFi devices in "client mode" (showing only
+  // Ethernet frames) by specifying the "device" parameter (see below).
+  // By specifying a channel, the script will find or create a "monitor
+  // mode" interface if one is available and produce an "over the air"
+  // packet capture.  The name of the output packet capture file is sent
+  // to the output file descriptor.
+  bool PacketCaptureStart(
+      const dbus::FileDescriptor& in_statfd,
+      const dbus::FileDescriptor& in_outfd,
+      const brillo::VariantDictionary& in_options,
+      std::string* out_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PacketCaptureStart",
+        error,
+        in_statfd,
+        in_outfd,
+        in_options);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_handle);
+  }
+
+  // Starts a packet capture with the specified options, with diagnostic
+  // status directed to the "statfd" file descriptor and packet capture
+  // data sent to the "outfd" file descriptor.  The returned opaque string
+  // functions as a handle for this particular packet capture.  Multiple
+  // captures can be running at once.  Captures can be initiated on
+  // Ethernet-like devices or WiFi devices in "client mode" (showing only
+  // Ethernet frames) by specifying the "device" parameter (see below).
+  // By specifying a channel, the script will find or create a "monitor
+  // mode" interface if one is available and produce an "over the air"
+  // packet capture.  The name of the output packet capture file is sent
+  // to the output file descriptor.
+  void PacketCaptureStartAsync(
+      const dbus::FileDescriptor& in_statfd,
+      const dbus::FileDescriptor& in_outfd,
+      const brillo::VariantDictionary& in_options,
+      const base::Callback<void(const std::string& /*handle*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PacketCaptureStart",
+        success_callback,
+        error_callback,
+        in_statfd,
+        in_outfd,
+        in_options);
+  }
+
+  // Stops a running packet capture.
+  bool PacketCaptureStop(
+      const std::string& in_handle,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PacketCaptureStop",
+        error,
+        in_handle);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Stops a running packet capture.
+  void PacketCaptureStopAsync(
+      const std::string& in_handle,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "PacketCaptureStop",
+        success_callback,
+        error_callback,
+        in_handle);
+  }
+
+  // Triggers show-task-states(T) SysRq.
+  // See https://www.kernel.org/doc/Documentation/sysrq.txt.
+  bool LogKernelTaskStates(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "LogKernelTaskStates",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Triggers show-task-states(T) SysRq.
+  // See https://www.kernel.org/doc/Documentation/sysrq.txt.
+  void LogKernelTaskStatesAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "LogKernelTaskStates",
+        success_callback,
+        error_callback);
+  }
+
+  // Triggers uploading of system crashes (the crash_sender program).
+  bool UploadCrashes(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "UploadCrashes",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Triggers uploading of system crashes (the crash_sender program).
+  void UploadCrashesAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "UploadCrashes",
+        success_callback,
+        error_callback);
+  }
+
+  // Removes rootfs verification. Requires a system reboot before it will
+  // take effect. Restricted to pre-owner dev mode.
+  bool RemoveRootfsVerification(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "RemoveRootfsVerification",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Removes rootfs verification. Requires a system reboot before it will
+  // take effect. Restricted to pre-owner dev mode.
+  void RemoveRootfsVerificationAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "RemoveRootfsVerification",
+        success_callback,
+        error_callback);
+  }
+
+  // Enables OS booting from a USB image. Restricted to pre-owner dev mode.
+  bool EnableBootFromUsb(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableBootFromUsb",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Enables OS booting from a USB image. Restricted to pre-owner dev mode.
+  void EnableBootFromUsbAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableBootFromUsb",
+        success_callback,
+        error_callback);
+  }
+
+  // Sets up sshd to provide an SSH server immediately and on future reboots.
+  // Also installs the test SSH keys to allow access by cros tools. Requires
+  // that rootfs verification has been removed. Restricted to pre-owner dev
+  // mode.
+  bool ConfigureSshServer(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "ConfigureSshServer",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Sets up sshd to provide an SSH server immediately and on future reboots.
+  // Also installs the test SSH keys to allow access by cros tools. Requires
+  // that rootfs verification has been removed. Restricted to pre-owner dev
+  // mode.
+  void ConfigureSshServerAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "ConfigureSshServer",
+        success_callback,
+        error_callback);
+  }
+
+  // Sets both the system and dev mode password for the indicated account.
+  // Restricted to pre-owner dev mode.
+  bool SetUserPassword(
+      const std::string& in_username,
+      const std::string& in_password,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SetUserPassword",
+        error,
+        in_username,
+        in_password);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Sets both the system and dev mode password for the indicated account.
+  // Restricted to pre-owner dev mode.
+  void SetUserPasswordAsync(
+      const std::string& in_username,
+      const std::string& in_password,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "SetUserPassword",
+        success_callback,
+        error_callback,
+        in_username,
+        in_password);
+  }
+
+  // Sets up Chrome for remote debugging. It will take effect after a reboot
+  // and using port 9222.
+  // Requires that rootfs verification has been removed. Restricted to
+  // pre-owner dev mode.
+  bool EnableChromeRemoteDebugging(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableChromeRemoteDebugging",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Sets up Chrome for remote debugging. It will take effect after a reboot
+  // and using port 9222.
+  // Requires that rootfs verification has been removed. Restricted to
+  // pre-owner dev mode.
+  void EnableChromeRemoteDebuggingAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableChromeRemoteDebugging",
+        success_callback,
+        error_callback);
+  }
+
+  // Convenience function to enable a predefined set of tools from the Chrome
+  // UI. Equivalent to calling these functions in order:
+  //   1. EnableBootFromUsb()
+  //   2. ConfigureSshServer()
+  //   3. SetUserPassword("root", root_password)
+  // Requires that rootfs verification has been removed. If any sub-function
+  // fails, this function will exit with an error without attempting any
+  // further configuration or rollback. Restricted to pre-owner dev mode.
+  bool EnableChromeDevFeatures(
+      const std::string& in_root_password,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableChromeDevFeatures",
+        error,
+        in_root_password);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Convenience function to enable a predefined set of tools from the Chrome
+  // UI. Equivalent to calling these functions in order:
+  //   1. EnableBootFromUsb()
+  //   2. ConfigureSshServer()
+  //   3. SetUserPassword("root", root_password)
+  // Requires that rootfs verification has been removed. If any sub-function
+  // fails, this function will exit with an error without attempting any
+  // further configuration or rollback. Restricted to pre-owner dev mode.
+  void EnableChromeDevFeaturesAsync(
+      const std::string& in_root_password,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableChromeDevFeatures",
+        success_callback,
+        error_callback,
+        in_root_password);
+  }
+
+  // Queries which dev features have been enabled. Each dev feature will be
+  // indicated by a bit flag in the return value. Flags are defined in the
+  // DevFeatureFlag enumeration. If the dev tools are unavailable (system is
+  // not in dev mode/pre-login state), the DEV_FEATURES_DISABLED flag will be
+  // set and the rest of the bits will always be set to 0.
+  bool QueryDevFeatures(
+      int32_t* out_features,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "QueryDevFeatures",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_features);
+  }
+
+  // Queries which dev features have been enabled. Each dev feature will be
+  // indicated by a bit flag in the return value. Flags are defined in the
+  // DevFeatureFlag enumeration. If the dev tools are unavailable (system is
+  // not in dev mode/pre-login state), the DEV_FEATURES_DISABLED flag will be
+  // set and the rest of the bits will always be set to 0.
+  void QueryDevFeaturesAsync(
+      const base::Callback<void(int32_t /*features*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "QueryDevFeatures",
+        success_callback,
+        error_callback);
+  }
+
+  // Allow uploading of device coredump files.
+  bool EnableDevCoredumpUpload(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableDevCoredumpUpload",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Allow uploading of device coredump files.
+  void EnableDevCoredumpUploadAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "EnableDevCoredumpUpload",
+        success_callback,
+        error_callback);
+  }
+
+  // Disallow uploading of device coredump files.
+  bool DisableDevCoredumpUpload(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "DisableDevCoredumpUpload",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // Disallow uploading of device coredump files.
+  void DisableDevCoredumpUploadAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.debugd",
+        "DisableDevCoredumpUpload",
+        success_callback,
+        error_callback);
+  }
+
+ private:
+  scoped_refptr<dbus::Bus> bus_;
+  const std::string service_name_{"org.chromium.debugd"};
+  const dbus::ObjectPath object_path_{"/org/chromium/debugd"};
+  dbus::ObjectProxy* dbus_object_proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(debugdProxy);
+};
+
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXIES_H
diff --git a/include/debugd/dbus-proxy-mocks.h b/include/debugd/dbus-proxy-mocks.h
new file mode 100644
index 0000000..042a9fd
--- /dev/null
+++ b/include/debugd/dbus-proxy-mocks.h
@@ -0,0 +1,453 @@
+// Automatic generation of D-Bus interface mock proxies for:
+//  - org.chromium.debugd
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXY_MOCKS_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXY_MOCKS_H
+#include <string>
+#include <vector>
+
+#include <base/callback_forward.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/any.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <gmock/gmock.h>
+
+#include "debugd/dbus-proxies.h"
+
+namespace org {
+namespace chromium {
+
+// Mock object for debugdProxyInterface.
+class debugdProxyMock : public debugdProxyInterface {
+ public:
+  debugdProxyMock() = default;
+
+  MOCK_METHOD6(PingStart,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    const std::string& /*in_destination*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    std::string* /*out_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(PingStartAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    const std::string& /*in_destination*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    const base::Callback<void(const std::string& /*handle*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(PingStop,
+               bool(const std::string& /*in_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(PingStopAsync,
+               void(const std::string& /*in_handle*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SystraceStart,
+               bool(const std::string& /*in_categories*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SystraceStartAsync,
+               void(const std::string& /*in_categories*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SystraceStop,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SystraceStopAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SystraceStatus,
+               bool(std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SystraceStatusAsync,
+               void(const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(TracePathStart,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    const std::string& /*in_destination*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    std::string* /*out_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(TracePathStartAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    const std::string& /*in_destination*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    const base::Callback<void(const std::string& /*handle*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(TracePathStop,
+               bool(const std::string& /*in_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(TracePathStopAsync,
+               void(const std::string& /*in_handle*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetRoutes,
+               bool(const brillo::VariantDictionary& /*in_options*/,
+                    std::vector<std::string>* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetRoutesAsync,
+               void(const brillo::VariantDictionary& /*in_options*/,
+                    const base::Callback<void(const std::vector<std::string>& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetModemStatus,
+               bool(std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetModemStatusAsync,
+               void(const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RunModemCommand,
+               bool(const std::string& /*in_command*/,
+                    std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RunModemCommandAsync,
+               void(const std::string& /*in_command*/,
+                    const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetNetworkStatus,
+               bool(std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetNetworkStatusAsync,
+               void(const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetWiMaxStatus,
+               bool(std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetWiMaxStatusAsync,
+               void(const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD7(GetPerfOutput,
+               bool(uint32_t /*in_duration_sec*/,
+                    const std::vector<std::string>& /*in_perf_args*/,
+                    int32_t* /*out_status*/,
+                    std::vector<uint8_t>* /*out_perf_data*/,
+                    std::vector<uint8_t>* /*out_perf_stat*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(GetPerfOutputAsync,
+               void(uint32_t /*in_duration_sec*/,
+                    const std::vector<std::string>& /*in_perf_args*/,
+                    const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(GetRandomPerfOutput,
+               bool(uint32_t /*in_duration_sec*/,
+                    int32_t* /*out_status*/,
+                    std::vector<uint8_t>* /*out_perf_data*/,
+                    std::vector<uint8_t>* /*out_perf_stat*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetRandomPerfOutputAsync,
+               void(uint32_t /*in_duration_sec*/,
+                    const base::Callback<void(int32_t /*status*/, const std::vector<uint8_t>& /*perf_data*/, const std::vector<uint8_t>& /*perf_stat*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetRichPerfData,
+               bool(uint32_t /*in_duration_sec*/,
+                    std::vector<uint8_t>* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetRichPerfDataAsync,
+               void(uint32_t /*in_duration_sec*/,
+                    const base::Callback<void(const std::vector<uint8_t>& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetDebugLogs,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetDebugLogsAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(DumpDebugLogs,
+               bool(bool /*in_is_compressed*/,
+                    const dbus::FileDescriptor& /*in_outfd*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(DumpDebugLogsAsync,
+               void(bool /*in_is_compressed*/,
+                    const dbus::FileDescriptor& /*in_outfd*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SetDebugMode,
+               bool(const std::string& /*in_subsystem*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetDebugModeAsync,
+               void(const std::string& /*in_subsystem*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetLog,
+               bool(const std::string& /*in_log*/,
+                    std::string* /*out_contents*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(GetLogAsync,
+               void(const std::string& /*in_log*/,
+                    const base::Callback<void(const std::string& /*contents*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetAllLogs,
+               bool(std::map<std::string, std::string>* /*out_logs*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetAllLogsAsync,
+               void(const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetFeedbackLogs,
+               bool(std::map<std::string, std::string>* /*out_logs*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetFeedbackLogsAsync,
+               void(const base::Callback<void(const std::map<std::string, std::string>& /*logs*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetUserLogFiles,
+               bool(std::map<std::string, std::string>* /*out_user_log_files*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetUserLogFilesAsync,
+               void(const base::Callback<void(const std::map<std::string, std::string>& /*user_log_files*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetExample,
+               bool(std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetExampleAsync,
+               void(const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetInterfaces,
+               bool(std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetInterfacesAsync,
+               void(const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(TestICMP,
+               bool(const std::string& /*in_host*/,
+                    std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(TestICMPAsync,
+               void(const std::string& /*in_host*/,
+                    const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(TestICMPWithOptions,
+               bool(const std::string& /*in_host*/,
+                    const std::map<std::string, std::string>& /*in_options*/,
+                    std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(TestICMPWithOptionsAsync,
+               void(const std::string& /*in_host*/,
+                    const std::map<std::string, std::string>& /*in_options*/,
+                    const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(BatteryFirmware,
+               bool(const std::string& /*in_option*/,
+                    std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(BatteryFirmwareAsync,
+               void(const std::string& /*in_option*/,
+                    const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(Smartctl,
+               bool(const std::string& /*in_option*/,
+                    std::string* /*out_result*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SmartctlAsync,
+               void(const std::string& /*in_option*/,
+                    const base::Callback<void(const std::string& /*result*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(MemtesterStart,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    uint32_t /*in_memory*/,
+                    std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(MemtesterStartAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    uint32_t /*in_memory*/,
+                    const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(MemtesterStop,
+               bool(const std::string& /*in_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(MemtesterStopAsync,
+               void(const std::string& /*in_handle*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(BadblocksStart,
+               bool(const dbus::FileDescriptor& /*in_outfd*/,
+                    std::string* /*out_status*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(BadblocksStartAsync,
+               void(const dbus::FileDescriptor& /*in_outfd*/,
+                    const base::Callback<void(const std::string& /*status*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(BadblocksStop,
+               bool(const std::string& /*in_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(BadblocksStopAsync,
+               void(const std::string& /*in_handle*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(PacketCaptureStart,
+               bool(const dbus::FileDescriptor& /*in_statfd*/,
+                    const dbus::FileDescriptor& /*in_outfd*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    std::string* /*out_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD6(PacketCaptureStartAsync,
+               void(const dbus::FileDescriptor& /*in_statfd*/,
+                    const dbus::FileDescriptor& /*in_outfd*/,
+                    const brillo::VariantDictionary& /*in_options*/,
+                    const base::Callback<void(const std::string& /*handle*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(PacketCaptureStop,
+               bool(const std::string& /*in_handle*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(PacketCaptureStopAsync,
+               void(const std::string& /*in_handle*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(LogKernelTaskStates,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(LogKernelTaskStatesAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(UploadCrashes,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(UploadCrashesAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(RemoveRootfsVerification,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RemoveRootfsVerificationAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(EnableBootFromUsb,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(EnableBootFromUsbAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(ConfigureSshServer,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(ConfigureSshServerAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetUserPassword,
+               bool(const std::string& /*in_username*/,
+                    const std::string& /*in_password*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(SetUserPasswordAsync,
+               void(const std::string& /*in_username*/,
+                    const std::string& /*in_password*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(EnableChromeRemoteDebugging,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(EnableChromeRemoteDebuggingAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(EnableChromeDevFeatures,
+               bool(const std::string& /*in_root_password*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(EnableChromeDevFeaturesAsync,
+               void(const std::string& /*in_root_password*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(QueryDevFeatures,
+               bool(int32_t* /*out_features*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(QueryDevFeaturesAsync,
+               void(const base::Callback<void(int32_t /*features*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(EnableDevCoredumpUpload,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(EnableDevCoredumpUploadAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(DisableDevCoredumpUpload,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(DisableDevCoredumpUploadAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(debugdProxyMock);
+};
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_DEBUGD_CLIENT_OUT_DEFAULT_GEN_INCLUDE_DEBUGD_DBUS_PROXY_MOCKS_H
diff --git a/include/power_manager/dbus-constants.h b/include/power_manager/dbus-constants.h
new file mode 100644
index 0000000..fa42cb1
--- /dev/null
+++ b/include/power_manager/dbus-constants.h
@@ -0,0 +1,66 @@
+// Copyright 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef SYSTEM_API_DBUS_POWER_MANAGER_DBUS_CONSTANTS_H_
+#define SYSTEM_API_DBUS_POWER_MANAGER_DBUS_CONSTANTS_H_
+
+namespace power_manager {
+// powerd
+const char kPowerManagerInterface[] = "org.chromium.PowerManager";
+const char kPowerManagerServicePath[] = "/org/chromium/PowerManager";
+const char kPowerManagerServiceName[] = "org.chromium.PowerManager";
+// Methods exposed by powerd.
+const char kDecreaseScreenBrightnessMethod[] = "DecreaseScreenBrightness";
+const char kIncreaseScreenBrightnessMethod[] = "IncreaseScreenBrightness";
+const char kGetScreenBrightnessPercentMethod[] = "GetScreenBrightnessPercent";
+const char kSetScreenBrightnessPercentMethod[] = "SetScreenBrightnessPercent";
+const char kDecreaseKeyboardBrightnessMethod[] = "DecreaseKeyboardBrightness";
+const char kIncreaseKeyboardBrightnessMethod[] = "IncreaseKeyboardBrightness";
+const char kRequestRestartMethod[] = "RequestRestart";
+const char kRequestShutdownMethod[] = "RequestShutdown";
+const char kRequestSuspendMethod[] = "RequestSuspend";
+const char kGetPowerSupplyPropertiesMethod[] = "GetPowerSupplyProperties";
+const char kHandleUserActivityMethod[] = "HandleUserActivity";
+const char kHandleVideoActivityMethod[] = "HandleVideoActivity";
+const char kSetIsProjectingMethod[] = "SetIsProjecting";
+const char kSetPolicyMethod[] = "SetPolicy";
+const char kSetPowerSourceMethod[] = "SetPowerSource";
+const char kRegisterSuspendDelayMethod[] = "RegisterSuspendDelay";
+const char kUnregisterSuspendDelayMethod[] = "UnregisterSuspendDelay";
+const char kHandleSuspendReadinessMethod[] = "HandleSuspendReadiness";
+const char kRegisterDarkSuspendDelayMethod[] = "RegisterDarkSuspendDelay";
+const char kUnregisterDarkSuspendDelayMethod[] = "UnregisterDarkSuspendDelay";
+const char kHandleDarkSuspendReadinessMethod[] = "HandleDarkSuspendReadiness";
+const char kHandlePowerButtonAcknowledgmentMethod[] =
+    "HandlePowerButtonAcknowledgment";
+const char kRecordDarkResumeWakeReasonMethod[] = "RecordDarkResumeWakeReason";
+// Signals emitted by powerd.
+const char kBrightnessChangedSignal[] = "BrightnessChanged";
+const char kKeyboardBrightnessChangedSignal[] = "KeyboardBrightnessChanged";
+const char kPeripheralBatteryStatusSignal[] = "PeripheralBatteryStatus";
+const char kPowerSupplyPollSignal[] = "PowerSupplyPoll";
+const char kSuspendImminentSignal[] = "SuspendImminent";
+const char kDarkSuspendImminentSignal[] = "DarkSuspendImminent";
+const char kSuspendDoneSignal[] = "SuspendDone";
+const char kInputEventSignal[] = "InputEvent";
+const char kIdleActionImminentSignal[] = "IdleActionImminent";
+const char kIdleActionDeferredSignal[] = "IdleActionDeferred";
+// Values
+const int kBrightnessTransitionGradual = 1;
+const int kBrightnessTransitionInstant = 2;
+enum UserActivityType {
+  USER_ACTIVITY_OTHER = 0,
+  USER_ACTIVITY_BRIGHTNESS_UP_KEY_PRESS = 1,
+  USER_ACTIVITY_BRIGHTNESS_DOWN_KEY_PRESS = 2,
+  USER_ACTIVITY_VOLUME_UP_KEY_PRESS = 3,
+  USER_ACTIVITY_VOLUME_DOWN_KEY_PRESS = 4,
+  USER_ACTIVITY_VOLUME_MUTE_KEY_PRESS = 5,
+};
+enum RequestRestartReason {
+  REQUEST_RESTART_FOR_USER = 0,
+  REQUEST_RESTART_FOR_UPDATE = 1,
+};
+}  // namespace power_manager
+
+#endif  // SYSTEM_API_DBUS_POWER_MANAGER_DBUS_CONSTANTS_H_
diff --git a/include/power_manager/dbus-proxies.h b/include/power_manager/dbus-proxies.h
new file mode 100644
index 0000000..e66848d
--- /dev/null
+++ b/include/power_manager/dbus-proxies.h
@@ -0,0 +1,1280 @@
+// Automatic generation of D-Bus interfaces:
+//  - org.chromium.PowerManager
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXIES_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXIES_H
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <base/memory/ref_counted.h>
+#include <brillo/any.h>
+#include <brillo/dbus/dbus_method_invoker.h>
+#include <brillo/dbus/dbus_property.h>
+#include <brillo/dbus/dbus_signal_handler.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <dbus/bus.h>
+#include <dbus/message.h>
+#include <dbus/object_manager.h>
+#include <dbus/object_path.h>
+#include <dbus/object_proxy.h>
+
+namespace org {
+namespace chromium {
+
+// Abstract interface proxy for org::chromium::PowerManager.
+class PowerManagerProxyInterface {
+ public:
+  virtual ~PowerManagerProxyInterface() = default;
+
+  virtual bool RequestShutdown(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RequestShutdownAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |reason| arg is a power_manager::RequestRestartReason value.
+  virtual bool RequestRestart(
+      int32_t in_reason,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |reason| arg is a power_manager::RequestRestartReason value.
+  virtual void RequestRestartAsync(
+      int32_t in_reason,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |external_wakeup_count| arg is optional, and it will call two
+  // different methods in the backend. This can't be expressed in the DBus
+  // Introspection XML file.
+  virtual bool RequestSuspend(
+      uint64_t in_external_wakeup_count,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |external_wakeup_count| arg is optional, and it will call two
+  // different methods in the backend. This can't be expressed in the DBus
+  // Introspection XML file.
+  virtual void RequestSuspendAsync(
+      uint64_t in_external_wakeup_count,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool DecreaseScreenBrightness(
+      bool in_allow_off,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void DecreaseScreenBrightnessAsync(
+      bool in_allow_off,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool IncreaseScreenBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void IncreaseScreenBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool GetScreenBrightnessPercent(
+      double* out_percent,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void GetScreenBrightnessPercentAsync(
+      const base::Callback<void(double /*percent*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |style| arg must be one of the values:
+  //   power_manager::kBrightnessTransitionGradual or
+  //   power_manager::kBrightnessTransitionInstant.
+  virtual bool SetScreenBrightnessPercent(
+      double in_percent,
+      int32_t in_style,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |style| arg must be one of the values:
+  //   power_manager::kBrightnessTransitionGradual or
+  //   power_manager::kBrightnessTransitionInstant.
+  virtual void SetScreenBrightnessPercentAsync(
+      double in_percent,
+      int32_t in_style,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool DecreaseKeyboardBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void DecreaseKeyboardBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool IncreaseKeyboardBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void IncreaseKeyboardBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerSupplyProperties protobuf.
+  virtual bool GetPowerSupplyProperties(
+      std::vector<uint8_t>* out_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerSupplyProperties protobuf.
+  virtual void GetPowerSupplyPropertiesAsync(
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool HandleVideoActivity(
+      bool in_fullscreen,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void HandleVideoActivityAsync(
+      bool in_fullscreen,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |type| arg is a power_manager::UserActivityType.
+  virtual bool HandleUserActivity(
+      int32_t in_type,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |type| arg is a power_manager::UserActivityType.
+  virtual void HandleUserActivityAsync(
+      int32_t in_type,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool SetIsProjecting(
+      bool in_is_projecting,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void SetIsProjectingAsync(
+      bool in_is_projecting,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerManagementPolicy protobuf.
+  virtual bool SetPolicy(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerManagementPolicy protobuf.
+  virtual void SetPolicyAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool SetPowerSource(
+      const std::string& in_id,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void SetPowerSourceAsync(
+      const std::string& in_id,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |timestamp_internal| arg is represented as the return value of
+  // base::TimeTicks::ToInternalValue().
+  virtual bool HandlePowerButtonAcknowledgment(
+      int64_t in_timestamp_internal,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |timestamp_internal| arg is represented as the return value of
+  // base::TimeTicks::ToInternalValue().
+  virtual void HandlePowerButtonAcknowledgmentAsync(
+      int64_t in_timestamp_internal,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  virtual bool RegisterSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      std::vector<uint8_t>* out_serialized_reply_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  virtual void RegisterSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  virtual bool UnregisterSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  virtual void UnregisterSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  virtual bool HandleSuspendReadiness(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  virtual void HandleSuspendReadinessAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  virtual bool RegisterDarkSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      std::vector<uint8_t>* out_serialized_reply_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  virtual void RegisterDarkSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  virtual bool UnregisterDarkSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  virtual void UnregisterDarkSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  virtual bool HandleDarkSuspendReadiness(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  virtual void HandleDarkSuspendReadinessAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::DarkResumeWakeReason protobuf.
+  virtual bool RecordDarkResumeWakeReason(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::DarkResumeWakeReason protobuf.
+  virtual void RecordDarkResumeWakeReasonAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RegisterBrightnessChangedSignalHandler(
+      const base::Callback<void(int32_t,
+                                bool)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterKeyboardBrightnessChangedSignalHandler(
+      const base::Callback<void(int32_t,
+                                bool)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterPeripheralBatteryStatusSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterPowerSupplyPollSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterSuspendImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterSuspendDoneSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterDarkSuspendImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterInputEventSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterIdleActionImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterIdleActionDeferredSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+};
+
+}  // namespace chromium
+}  // namespace org
+
+namespace org {
+namespace chromium {
+
+// Interface proxy for org::chromium::PowerManager.
+class PowerManagerProxy final : public PowerManagerProxyInterface {
+ public:
+  PowerManagerProxy(const scoped_refptr<dbus::Bus>& bus) :
+      bus_{bus},
+      dbus_object_proxy_{
+          bus_->GetObjectProxy(service_name_, object_path_)} {
+  }
+
+  ~PowerManagerProxy() override {
+    bus_->RemoveObjectProxy(
+        service_name_, object_path_, base::Bind(&base::DoNothing));
+  }
+
+  void RegisterBrightnessChangedSignalHandler(
+      const base::Callback<void(int32_t,
+                                bool)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "BrightnessChanged",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterKeyboardBrightnessChangedSignalHandler(
+      const base::Callback<void(int32_t,
+                                bool)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "KeyboardBrightnessChanged",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterPeripheralBatteryStatusSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "PeripheralBatteryStatus",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterPowerSupplyPollSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "PowerSupplyPoll",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterSuspendImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SuspendImminent",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterSuspendDoneSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SuspendDone",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterDarkSuspendImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "DarkSuspendImminent",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterInputEventSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "InputEvent",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterIdleActionImminentSignalHandler(
+      const base::Callback<void(const std::vector<uint8_t>&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IdleActionImminent",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterIdleActionDeferredSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IdleActionDeferred",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void ReleaseObjectProxy(const base::Closure& callback) {
+    bus_->RemoveObjectProxy(service_name_, object_path_, callback);
+  }
+
+  const dbus::ObjectPath& GetObjectPath() const {
+    return object_path_;
+  }
+
+  dbus::ObjectProxy* GetObjectProxy() const { return dbus_object_proxy_; }
+
+  bool RequestShutdown(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestShutdown",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void RequestShutdownAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestShutdown",
+        success_callback,
+        error_callback);
+  }
+
+  // The |reason| arg is a power_manager::RequestRestartReason value.
+  bool RequestRestart(
+      int32_t in_reason,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestRestart",
+        error,
+        in_reason);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |reason| arg is a power_manager::RequestRestartReason value.
+  void RequestRestartAsync(
+      int32_t in_reason,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestRestart",
+        success_callback,
+        error_callback,
+        in_reason);
+  }
+
+  // The |external_wakeup_count| arg is optional, and it will call two
+  // different methods in the backend. This can't be expressed in the DBus
+  // Introspection XML file.
+  bool RequestSuspend(
+      uint64_t in_external_wakeup_count,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestSuspend",
+        error,
+        in_external_wakeup_count);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |external_wakeup_count| arg is optional, and it will call two
+  // different methods in the backend. This can't be expressed in the DBus
+  // Introspection XML file.
+  void RequestSuspendAsync(
+      uint64_t in_external_wakeup_count,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RequestSuspend",
+        success_callback,
+        error_callback,
+        in_external_wakeup_count);
+  }
+
+  bool DecreaseScreenBrightness(
+      bool in_allow_off,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "DecreaseScreenBrightness",
+        error,
+        in_allow_off);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void DecreaseScreenBrightnessAsync(
+      bool in_allow_off,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "DecreaseScreenBrightness",
+        success_callback,
+        error_callback,
+        in_allow_off);
+  }
+
+  bool IncreaseScreenBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IncreaseScreenBrightness",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void IncreaseScreenBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IncreaseScreenBrightness",
+        success_callback,
+        error_callback);
+  }
+
+  bool GetScreenBrightnessPercent(
+      double* out_percent,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "GetScreenBrightnessPercent",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_percent);
+  }
+
+  void GetScreenBrightnessPercentAsync(
+      const base::Callback<void(double /*percent*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "GetScreenBrightnessPercent",
+        success_callback,
+        error_callback);
+  }
+
+  // The |style| arg must be one of the values:
+  //   power_manager::kBrightnessTransitionGradual or
+  //   power_manager::kBrightnessTransitionInstant.
+  bool SetScreenBrightnessPercent(
+      double in_percent,
+      int32_t in_style,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetScreenBrightnessPercent",
+        error,
+        in_percent,
+        in_style);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |style| arg must be one of the values:
+  //   power_manager::kBrightnessTransitionGradual or
+  //   power_manager::kBrightnessTransitionInstant.
+  void SetScreenBrightnessPercentAsync(
+      double in_percent,
+      int32_t in_style,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetScreenBrightnessPercent",
+        success_callback,
+        error_callback,
+        in_percent,
+        in_style);
+  }
+
+  bool DecreaseKeyboardBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "DecreaseKeyboardBrightness",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void DecreaseKeyboardBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "DecreaseKeyboardBrightness",
+        success_callback,
+        error_callback);
+  }
+
+  bool IncreaseKeyboardBrightness(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IncreaseKeyboardBrightness",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void IncreaseKeyboardBrightnessAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "IncreaseKeyboardBrightness",
+        success_callback,
+        error_callback);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerSupplyProperties protobuf.
+  bool GetPowerSupplyProperties(
+      std::vector<uint8_t>* out_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "GetPowerSupplyProperties",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_serialized_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerSupplyProperties protobuf.
+  void GetPowerSupplyPropertiesAsync(
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "GetPowerSupplyProperties",
+        success_callback,
+        error_callback);
+  }
+
+  bool HandleVideoActivity(
+      bool in_fullscreen,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleVideoActivity",
+        error,
+        in_fullscreen);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void HandleVideoActivityAsync(
+      bool in_fullscreen,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleVideoActivity",
+        success_callback,
+        error_callback,
+        in_fullscreen);
+  }
+
+  // The |type| arg is a power_manager::UserActivityType.
+  bool HandleUserActivity(
+      int32_t in_type,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleUserActivity",
+        error,
+        in_type);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |type| arg is a power_manager::UserActivityType.
+  void HandleUserActivityAsync(
+      int32_t in_type,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleUserActivity",
+        success_callback,
+        error_callback,
+        in_type);
+  }
+
+  bool SetIsProjecting(
+      bool in_is_projecting,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetIsProjecting",
+        error,
+        in_is_projecting);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void SetIsProjectingAsync(
+      bool in_is_projecting,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetIsProjecting",
+        success_callback,
+        error_callback,
+        in_is_projecting);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerManagementPolicy protobuf.
+  bool SetPolicy(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetPolicy",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::PowerManagementPolicy protobuf.
+  void SetPolicyAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetPolicy",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+  bool SetPowerSource(
+      const std::string& in_id,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetPowerSource",
+        error,
+        in_id);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void SetPowerSourceAsync(
+      const std::string& in_id,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "SetPowerSource",
+        success_callback,
+        error_callback,
+        in_id);
+  }
+
+  // The |timestamp_internal| arg is represented as the return value of
+  // base::TimeTicks::ToInternalValue().
+  bool HandlePowerButtonAcknowledgment(
+      int64_t in_timestamp_internal,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandlePowerButtonAcknowledgment",
+        error,
+        in_timestamp_internal);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |timestamp_internal| arg is represented as the return value of
+  // base::TimeTicks::ToInternalValue().
+  void HandlePowerButtonAcknowledgmentAsync(
+      int64_t in_timestamp_internal,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandlePowerButtonAcknowledgment",
+        success_callback,
+        error_callback,
+        in_timestamp_internal);
+  }
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  bool RegisterSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      std::vector<uint8_t>* out_serialized_reply_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RegisterSuspendDelay",
+        error,
+        in_serialized_request_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_serialized_reply_proto);
+  }
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  void RegisterSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RegisterSuspendDelay",
+        success_callback,
+        error_callback,
+        in_serialized_request_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  bool UnregisterSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "UnregisterSuspendDelay",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  void UnregisterSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "UnregisterSuspendDelay",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  bool HandleSuspendReadiness(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleSuspendReadiness",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  void HandleSuspendReadinessAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleSuspendReadiness",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  bool RegisterDarkSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      std::vector<uint8_t>* out_serialized_reply_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RegisterDarkSuspendDelay",
+        error,
+        in_serialized_request_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_serialized_reply_proto);
+  }
+
+  // The |serialized_request_proto| arg is a serialized
+  // power_manager::RegisterSuspendDelayRequest protobuf.
+  // The |serialized_reply_proto| arg is a serialized
+  // RegisterSuspendDelayReply protobuf.
+  void RegisterDarkSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_request_proto,
+      const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RegisterDarkSuspendDelay",
+        success_callback,
+        error_callback,
+        in_serialized_request_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  bool UnregisterDarkSuspendDelay(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "UnregisterDarkSuspendDelay",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::UnregisterSuspendDelayRequest protobuf.
+  void UnregisterDarkSuspendDelayAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "UnregisterDarkSuspendDelay",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  bool HandleDarkSuspendReadiness(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleDarkSuspendReadiness",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::SuspendReadinessInfo protobuf.
+  void HandleDarkSuspendReadinessAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "HandleDarkSuspendReadiness",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::DarkResumeWakeReason protobuf.
+  bool RecordDarkResumeWakeReason(
+      const std::vector<uint8_t>& in_serialized_proto,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RecordDarkResumeWakeReason",
+        error,
+        in_serialized_proto);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  // The |serialized_proto| arg is a serialized
+  // power_manager::DarkResumeWakeReason protobuf.
+  void RecordDarkResumeWakeReasonAsync(
+      const std::vector<uint8_t>& in_serialized_proto,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.PowerManager",
+        "RecordDarkResumeWakeReason",
+        success_callback,
+        error_callback,
+        in_serialized_proto);
+  }
+
+ private:
+  scoped_refptr<dbus::Bus> bus_;
+  const std::string service_name_{"org.chromium.PowerManager"};
+  const dbus::ObjectPath object_path_{"/org/chromium/PowerManager"};
+  dbus::ObjectProxy* dbus_object_proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(PowerManagerProxy);
+};
+
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXIES_H
diff --git a/include/power_manager/dbus-proxy-mocks.h b/include/power_manager/dbus-proxy-mocks.h
new file mode 100644
index 0000000..d4e3dd0
--- /dev/null
+++ b/include/power_manager/dbus-proxy-mocks.h
@@ -0,0 +1,266 @@
+// Automatic generation of D-Bus interface mock proxies for:
+//  - org.chromium.PowerManager
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXY_MOCKS_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXY_MOCKS_H
+#include <string>
+#include <vector>
+
+#include <base/callback_forward.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/any.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <gmock/gmock.h>
+
+#include "power_manager/dbus-proxies.h"
+
+namespace org {
+namespace chromium {
+
+// Mock object for PowerManagerProxyInterface.
+class PowerManagerProxyMock : public PowerManagerProxyInterface {
+ public:
+  PowerManagerProxyMock() = default;
+
+  MOCK_METHOD2(RequestShutdown,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RequestShutdownAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RequestRestart,
+               bool(int32_t /*in_reason*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RequestRestartAsync,
+               void(int32_t /*in_reason*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RequestSuspend,
+               bool(uint64_t /*in_external_wakeup_count*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RequestSuspendAsync,
+               void(uint64_t /*in_external_wakeup_count*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(DecreaseScreenBrightness,
+               bool(bool /*in_allow_off*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(DecreaseScreenBrightnessAsync,
+               void(bool /*in_allow_off*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(IncreaseScreenBrightness,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(IncreaseScreenBrightnessAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetScreenBrightnessPercent,
+               bool(double* /*out_percent*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetScreenBrightnessPercentAsync,
+               void(const base::Callback<void(double /*percent*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetScreenBrightnessPercent,
+               bool(double /*in_percent*/,
+                    int32_t /*in_style*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(SetScreenBrightnessPercentAsync,
+               void(double /*in_percent*/,
+                    int32_t /*in_style*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(DecreaseKeyboardBrightness,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(DecreaseKeyboardBrightnessAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(IncreaseKeyboardBrightness,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(IncreaseKeyboardBrightnessAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetPowerSupplyProperties,
+               bool(std::vector<uint8_t>* /*out_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetPowerSupplyPropertiesAsync,
+               void(const base::Callback<void(const std::vector<uint8_t>& /*serialized_proto*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleVideoActivity,
+               bool(bool /*in_fullscreen*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(HandleVideoActivityAsync,
+               void(bool /*in_fullscreen*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleUserActivity,
+               bool(int32_t /*in_type*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(HandleUserActivityAsync,
+               void(int32_t /*in_type*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SetIsProjecting,
+               bool(bool /*in_is_projecting*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetIsProjectingAsync,
+               void(bool /*in_is_projecting*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SetPolicy,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetPolicyAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(SetPowerSource,
+               bool(const std::string& /*in_id*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetPowerSourceAsync,
+               void(const std::string& /*in_id*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandlePowerButtonAcknowledgment,
+               bool(int64_t /*in_timestamp_internal*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(HandlePowerButtonAcknowledgmentAsync,
+               void(int64_t /*in_timestamp_internal*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RegisterSuspendDelay,
+               bool(const std::vector<uint8_t>& /*in_serialized_request_proto*/,
+                    std::vector<uint8_t>* /*out_serialized_reply_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RegisterSuspendDelayAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_request_proto*/,
+                    const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(UnregisterSuspendDelay,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(UnregisterSuspendDelayAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleSuspendReadiness,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(HandleSuspendReadinessAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RegisterDarkSuspendDelay,
+               bool(const std::vector<uint8_t>& /*in_serialized_request_proto*/,
+                    std::vector<uint8_t>* /*out_serialized_reply_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RegisterDarkSuspendDelayAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_request_proto*/,
+                    const base::Callback<void(const std::vector<uint8_t>& /*serialized_reply_proto*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(UnregisterDarkSuspendDelay,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(UnregisterDarkSuspendDelayAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleDarkSuspendReadiness,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(HandleDarkSuspendReadinessAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RecordDarkResumeWakeReason,
+               bool(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RecordDarkResumeWakeReasonAsync,
+               void(const std::vector<uint8_t>& /*in_serialized_proto*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(RegisterBrightnessChangedSignalHandler,
+               void(const base::Callback<void(int32_t,
+                                              bool)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterKeyboardBrightnessChangedSignalHandler,
+               void(const base::Callback<void(int32_t,
+                                              bool)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterPeripheralBatteryStatusSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterPowerSupplyPollSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterSuspendImminentSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterSuspendDoneSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterDarkSuspendImminentSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterInputEventSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterIdleActionImminentSignalHandler,
+               void(const base::Callback<void(const std::vector<uint8_t>&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterIdleActionDeferredSignalHandler,
+               void(const base::Closure& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(PowerManagerProxyMock);
+};
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_TMP_PORTAGE_CHROMEOS_BASE_POWER_MANAGER_9999_WORK_BUILD_OUT_DEFAULT_GEN_INCLUDE_POWER_MANAGER_DBUS_PROXY_MOCKS_H
diff --git a/include/session_manager/dbus-proxies.h b/include/session_manager/dbus-proxies.h
new file mode 100644
index 0000000..2ca0128
--- /dev/null
+++ b/include/session_manager/dbus-proxies.h
@@ -0,0 +1,1065 @@
+// Automatic generation of D-Bus interfaces:
+//  - org.chromium.SessionManagerInterface
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXIES_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXIES_H
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <base/memory/ref_counted.h>
+#include <brillo/any.h>
+#include <brillo/dbus/dbus_method_invoker.h>
+#include <brillo/dbus/dbus_property.h>
+#include <brillo/dbus/dbus_signal_handler.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <dbus/bus.h>
+#include <dbus/message.h>
+#include <dbus/object_manager.h>
+#include <dbus/object_path.h>
+#include <dbus/object_proxy.h>
+
+namespace org {
+namespace chromium {
+
+// Abstract interface proxy for org::chromium::SessionManagerInterface.
+class SessionManagerInterfaceProxyInterface {
+ public:
+  virtual ~SessionManagerInterfaceProxyInterface() = default;
+
+  virtual bool EmitLoginPromptVisible(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void EmitLoginPromptVisibleAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool EnableChromeTesting(
+      bool in_force_relaunch,
+      const std::vector<std::string>& in_extra_arguments,
+      std::string* out_filepath,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void EnableChromeTestingAsync(
+      bool in_force_relaunch,
+      const std::vector<std::string>& in_extra_arguments,
+      const base::Callback<void(const std::string& /*filepath*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StartSession(
+      const std::string& in_email_address,
+      const std::string& in_unique_identifier,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StartSessionAsync(
+      const std::string& in_email_address,
+      const std::string& in_unique_identifier,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StopSession(
+      const std::string& in_unique_identifier,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StopSessionAsync(
+      const std::string& in_unique_identifier,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StorePolicy(
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StorePolicyAsync(
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RetrievePolicy(
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RetrievePolicyAsync(
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StorePolicyForUser(
+      const std::string& in_user_email,
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StorePolicyForUserAsync(
+      const std::string& in_user_email,
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RetrievePolicyForUser(
+      const std::string& in_user_email,
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RetrievePolicyForUserAsync(
+      const std::string& in_user_email,
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StoreDeviceLocalAccountPolicy(
+      const std::string& in_account_id,
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StoreDeviceLocalAccountPolicyAsync(
+      const std::string& in_account_id,
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RetrieveDeviceLocalAccountPolicy(
+      const std::string& in_account_id,
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RetrieveDeviceLocalAccountPolicyAsync(
+      const std::string& in_account_id,
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RetrieveSessionState(
+      std::string* out_state,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RetrieveSessionStateAsync(
+      const base::Callback<void(const std::string& /*state*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RetrieveActiveSessions(
+      std::map<std::string, std::string>* out_sessions,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RetrieveActiveSessionsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*sessions*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool HandleSupervisedUserCreationStarting(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void HandleSupervisedUserCreationStartingAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool HandleSupervisedUserCreationFinished(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void HandleSupervisedUserCreationFinishedAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool LockScreen(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void LockScreenAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool HandleLockScreenShown(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void HandleLockScreenShownAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool HandleLockScreenDismissed(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void HandleLockScreenDismissedAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool RestartJob(
+      const dbus::FileDescriptor& in_cred_fd,
+      const std::vector<std::string>& in_argv,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RestartJobAsync(
+      const dbus::FileDescriptor& in_cred_fd,
+      const std::vector<std::string>& in_argv,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool StartDeviceWipe(
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void StartDeviceWipeAsync(
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool SetFlagsForUser(
+      const std::string& in_user_email,
+      const std::vector<std::string>& in_flags,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void SetFlagsForUserAsync(
+      const std::string& in_user_email,
+      const std::vector<std::string>& in_flags,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool GetServerBackedStateKeys(
+      std::vector<std::vector<uint8_t>>* out_state_keys,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void GetServerBackedStateKeysAsync(
+      const base::Callback<void(const std::vector<std::vector<uint8_t>>& /*state_keys*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual bool InitMachineInfo(
+      const std::string& in_data,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void InitMachineInfoAsync(
+      const std::string& in_data,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) = 0;
+
+  virtual void RegisterLoginPromptVisibleSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterSessionStateChangedSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterSetOwnerKeyCompleteSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterPropertyChangeCompleteSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterScreenIsLockedSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+
+  virtual void RegisterScreenIsUnlockedSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) = 0;
+};
+
+}  // namespace chromium
+}  // namespace org
+
+namespace org {
+namespace chromium {
+
+// Interface proxy for org::chromium::SessionManagerInterface.
+class SessionManagerInterfaceProxy final : public SessionManagerInterfaceProxyInterface {
+ public:
+  SessionManagerInterfaceProxy(const scoped_refptr<dbus::Bus>& bus) :
+      bus_{bus},
+      dbus_object_proxy_{
+          bus_->GetObjectProxy(service_name_, object_path_)} {
+  }
+
+  ~SessionManagerInterfaceProxy() override {
+    bus_->RemoveObjectProxy(
+        service_name_, object_path_, base::Bind(&base::DoNothing));
+  }
+
+  void RegisterLoginPromptVisibleSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "LoginPromptVisible",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterSessionStateChangedSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "SessionStateChanged",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterSetOwnerKeyCompleteSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "SetOwnerKeyComplete",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterPropertyChangeCompleteSignalHandler(
+      const base::Callback<void(const std::string&)>& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "PropertyChangeComplete",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterScreenIsLockedSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "ScreenIsLocked",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void RegisterScreenIsUnlockedSignalHandler(
+      const base::Closure& signal_callback,
+      dbus::ObjectProxy::OnConnectedCallback on_connected_callback) override {
+    brillo::dbus_utils::ConnectToSignal(
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "ScreenIsUnlocked",
+        signal_callback,
+        on_connected_callback);
+  }
+
+  void ReleaseObjectProxy(const base::Closure& callback) {
+    bus_->RemoveObjectProxy(service_name_, object_path_, callback);
+  }
+
+  const dbus::ObjectPath& GetObjectPath() const {
+    return object_path_;
+  }
+
+  dbus::ObjectProxy* GetObjectProxy() const { return dbus_object_proxy_; }
+
+  bool EmitLoginPromptVisible(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "EmitLoginPromptVisible",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void EmitLoginPromptVisibleAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "EmitLoginPromptVisible",
+        success_callback,
+        error_callback);
+  }
+
+  bool EnableChromeTesting(
+      bool in_force_relaunch,
+      const std::vector<std::string>& in_extra_arguments,
+      std::string* out_filepath,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "EnableChromeTesting",
+        error,
+        in_force_relaunch,
+        in_extra_arguments);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_filepath);
+  }
+
+  void EnableChromeTestingAsync(
+      bool in_force_relaunch,
+      const std::vector<std::string>& in_extra_arguments,
+      const base::Callback<void(const std::string& /*filepath*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "EnableChromeTesting",
+        success_callback,
+        error_callback,
+        in_force_relaunch,
+        in_extra_arguments);
+  }
+
+  bool StartSession(
+      const std::string& in_email_address,
+      const std::string& in_unique_identifier,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StartSession",
+        error,
+        in_email_address,
+        in_unique_identifier);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StartSessionAsync(
+      const std::string& in_email_address,
+      const std::string& in_unique_identifier,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StartSession",
+        success_callback,
+        error_callback,
+        in_email_address,
+        in_unique_identifier);
+  }
+
+  bool StopSession(
+      const std::string& in_unique_identifier,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StopSession",
+        error,
+        in_unique_identifier);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StopSessionAsync(
+      const std::string& in_unique_identifier,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StopSession",
+        success_callback,
+        error_callback,
+        in_unique_identifier);
+  }
+
+  bool StorePolicy(
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StorePolicy",
+        error,
+        in_policy_blob);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StorePolicyAsync(
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StorePolicy",
+        success_callback,
+        error_callback,
+        in_policy_blob);
+  }
+
+  bool RetrievePolicy(
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrievePolicy",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_policy_blob);
+  }
+
+  void RetrievePolicyAsync(
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrievePolicy",
+        success_callback,
+        error_callback);
+  }
+
+  bool StorePolicyForUser(
+      const std::string& in_user_email,
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StorePolicyForUser",
+        error,
+        in_user_email,
+        in_policy_blob);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StorePolicyForUserAsync(
+      const std::string& in_user_email,
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StorePolicyForUser",
+        success_callback,
+        error_callback,
+        in_user_email,
+        in_policy_blob);
+  }
+
+  bool RetrievePolicyForUser(
+      const std::string& in_user_email,
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrievePolicyForUser",
+        error,
+        in_user_email);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_policy_blob);
+  }
+
+  void RetrievePolicyForUserAsync(
+      const std::string& in_user_email,
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrievePolicyForUser",
+        success_callback,
+        error_callback,
+        in_user_email);
+  }
+
+  bool StoreDeviceLocalAccountPolicy(
+      const std::string& in_account_id,
+      const std::vector<uint8_t>& in_policy_blob,
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StoreDeviceLocalAccountPolicy",
+        error,
+        in_account_id,
+        in_policy_blob);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StoreDeviceLocalAccountPolicyAsync(
+      const std::string& in_account_id,
+      const std::vector<uint8_t>& in_policy_blob,
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StoreDeviceLocalAccountPolicy",
+        success_callback,
+        error_callback,
+        in_account_id,
+        in_policy_blob);
+  }
+
+  bool RetrieveDeviceLocalAccountPolicy(
+      const std::string& in_account_id,
+      std::vector<uint8_t>* out_policy_blob,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveDeviceLocalAccountPolicy",
+        error,
+        in_account_id);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_policy_blob);
+  }
+
+  void RetrieveDeviceLocalAccountPolicyAsync(
+      const std::string& in_account_id,
+      const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveDeviceLocalAccountPolicy",
+        success_callback,
+        error_callback,
+        in_account_id);
+  }
+
+  bool RetrieveSessionState(
+      std::string* out_state,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveSessionState",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_state);
+  }
+
+  void RetrieveSessionStateAsync(
+      const base::Callback<void(const std::string& /*state*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveSessionState",
+        success_callback,
+        error_callback);
+  }
+
+  bool RetrieveActiveSessions(
+      std::map<std::string, std::string>* out_sessions,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveActiveSessions",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_sessions);
+  }
+
+  void RetrieveActiveSessionsAsync(
+      const base::Callback<void(const std::map<std::string, std::string>& /*sessions*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RetrieveActiveSessions",
+        success_callback,
+        error_callback);
+  }
+
+  bool HandleSupervisedUserCreationStarting(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleSupervisedUserCreationStarting",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void HandleSupervisedUserCreationStartingAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleSupervisedUserCreationStarting",
+        success_callback,
+        error_callback);
+  }
+
+  bool HandleSupervisedUserCreationFinished(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleSupervisedUserCreationFinished",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void HandleSupervisedUserCreationFinishedAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleSupervisedUserCreationFinished",
+        success_callback,
+        error_callback);
+  }
+
+  bool LockScreen(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "LockScreen",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void LockScreenAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "LockScreen",
+        success_callback,
+        error_callback);
+  }
+
+  bool HandleLockScreenShown(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleLockScreenShown",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void HandleLockScreenShownAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleLockScreenShown",
+        success_callback,
+        error_callback);
+  }
+
+  bool HandleLockScreenDismissed(
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleLockScreenDismissed",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void HandleLockScreenDismissedAsync(
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "HandleLockScreenDismissed",
+        success_callback,
+        error_callback);
+  }
+
+  bool RestartJob(
+      const dbus::FileDescriptor& in_cred_fd,
+      const std::vector<std::string>& in_argv,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RestartJob",
+        error,
+        in_cred_fd,
+        in_argv);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void RestartJobAsync(
+      const dbus::FileDescriptor& in_cred_fd,
+      const std::vector<std::string>& in_argv,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "RestartJob",
+        success_callback,
+        error_callback,
+        in_cred_fd,
+        in_argv);
+  }
+
+  bool StartDeviceWipe(
+      bool* out_done,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StartDeviceWipe",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_done);
+  }
+
+  void StartDeviceWipeAsync(
+      const base::Callback<void(bool /*done*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "StartDeviceWipe",
+        success_callback,
+        error_callback);
+  }
+
+  bool SetFlagsForUser(
+      const std::string& in_user_email,
+      const std::vector<std::string>& in_flags,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "SetFlagsForUser",
+        error,
+        in_user_email,
+        in_flags);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void SetFlagsForUserAsync(
+      const std::string& in_user_email,
+      const std::vector<std::string>& in_flags,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "SetFlagsForUser",
+        success_callback,
+        error_callback,
+        in_user_email,
+        in_flags);
+  }
+
+  bool GetServerBackedStateKeys(
+      std::vector<std::vector<uint8_t>>* out_state_keys,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "GetServerBackedStateKeys",
+        error);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error, out_state_keys);
+  }
+
+  void GetServerBackedStateKeysAsync(
+      const base::Callback<void(const std::vector<std::vector<uint8_t>>& /*state_keys*/)>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "GetServerBackedStateKeys",
+        success_callback,
+        error_callback);
+  }
+
+  bool InitMachineInfo(
+      const std::string& in_data,
+      brillo::ErrorPtr* error,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    auto response = brillo::dbus_utils::CallMethodAndBlockWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "InitMachineInfo",
+        error,
+        in_data);
+    return response && brillo::dbus_utils::ExtractMethodCallResults(
+        response.get(), error);
+  }
+
+  void InitMachineInfoAsync(
+      const std::string& in_data,
+      const base::Callback<void()>& success_callback,
+      const base::Callback<void(brillo::Error*)>& error_callback,
+      int timeout_ms = dbus::ObjectProxy::TIMEOUT_USE_DEFAULT) override {
+    brillo::dbus_utils::CallMethodWithTimeout(
+        timeout_ms,
+        dbus_object_proxy_,
+        "org.chromium.SessionManagerInterface",
+        "InitMachineInfo",
+        success_callback,
+        error_callback,
+        in_data);
+  }
+
+ private:
+  scoped_refptr<dbus::Bus> bus_;
+  const std::string service_name_{"org.chromium.SessionManager"};
+  const dbus::ObjectPath object_path_{"/org/chromium/SessionManager"};
+  dbus::ObjectProxy* dbus_object_proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(SessionManagerInterfaceProxy);
+};
+
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXIES_H
diff --git a/include/session_manager/dbus-proxy-mocks.h b/include/session_manager/dbus-proxy-mocks.h
new file mode 100644
index 0000000..2b6ce4d
--- /dev/null
+++ b/include/session_manager/dbus-proxy-mocks.h
@@ -0,0 +1,252 @@
+// Automatic generation of D-Bus interface mock proxies for:
+//  - org.chromium.SessionManagerInterface
+#ifndef ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXY_MOCKS_H
+#define ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXY_MOCKS_H
+#include <string>
+#include <vector>
+
+#include <base/callback_forward.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/any.h>
+#include <brillo/errors/error.h>
+#include <brillo/variant_dictionary.h>
+#include <gmock/gmock.h>
+
+#include "session_manager/dbus-proxies.h"
+
+namespace org {
+namespace chromium {
+
+// Mock object for SessionManagerInterfaceProxyInterface.
+class SessionManagerInterfaceProxyMock : public SessionManagerInterfaceProxyInterface {
+ public:
+  SessionManagerInterfaceProxyMock() = default;
+
+  MOCK_METHOD2(EmitLoginPromptVisible,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(EmitLoginPromptVisibleAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(EnableChromeTesting,
+               bool(bool /*in_force_relaunch*/,
+                    const std::vector<std::string>& /*in_extra_arguments*/,
+                    std::string* /*out_filepath*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(EnableChromeTestingAsync,
+               void(bool /*in_force_relaunch*/,
+                    const std::vector<std::string>& /*in_extra_arguments*/,
+                    const base::Callback<void(const std::string& /*filepath*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StartSession,
+               bool(const std::string& /*in_email_address*/,
+                    const std::string& /*in_unique_identifier*/,
+                    bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StartSessionAsync,
+               void(const std::string& /*in_email_address*/,
+                    const std::string& /*in_unique_identifier*/,
+                    const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(StopSession,
+               bool(const std::string& /*in_unique_identifier*/,
+                    bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(StopSessionAsync,
+               void(const std::string& /*in_unique_identifier*/,
+                    const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(StorePolicy,
+               bool(const std::vector<uint8_t>& /*in_policy_blob*/,
+                    bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(StorePolicyAsync,
+               void(const std::vector<uint8_t>& /*in_policy_blob*/,
+                    const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrievePolicy,
+               bool(std::vector<uint8_t>* /*out_policy_blob*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrievePolicyAsync,
+               void(const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StorePolicyForUser,
+               bool(const std::string& /*in_user_email*/,
+                    const std::vector<uint8_t>& /*in_policy_blob*/,
+                    bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StorePolicyForUserAsync,
+               void(const std::string& /*in_user_email*/,
+                    const std::vector<uint8_t>& /*in_policy_blob*/,
+                    const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RetrievePolicyForUser,
+               bool(const std::string& /*in_user_email*/,
+                    std::vector<uint8_t>* /*out_policy_blob*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RetrievePolicyForUserAsync,
+               void(const std::string& /*in_user_email*/,
+                    const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StoreDeviceLocalAccountPolicy,
+               bool(const std::string& /*in_account_id*/,
+                    const std::vector<uint8_t>& /*in_policy_blob*/,
+                    bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(StoreDeviceLocalAccountPolicyAsync,
+               void(const std::string& /*in_account_id*/,
+                    const std::vector<uint8_t>& /*in_policy_blob*/,
+                    const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RetrieveDeviceLocalAccountPolicy,
+               bool(const std::string& /*in_account_id*/,
+                    std::vector<uint8_t>* /*out_policy_blob*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RetrieveDeviceLocalAccountPolicyAsync,
+               void(const std::string& /*in_account_id*/,
+                    const base::Callback<void(const std::vector<uint8_t>& /*policy_blob*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrieveSessionState,
+               bool(std::string* /*out_state*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrieveSessionStateAsync,
+               void(const base::Callback<void(const std::string& /*state*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrieveActiveSessions,
+               bool(std::map<std::string, std::string>* /*out_sessions*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(RetrieveActiveSessionsAsync,
+               void(const base::Callback<void(const std::map<std::string, std::string>& /*sessions*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(HandleSupervisedUserCreationStarting,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleSupervisedUserCreationStartingAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(HandleSupervisedUserCreationFinished,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleSupervisedUserCreationFinishedAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(LockScreen,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(LockScreenAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(HandleLockScreenShown,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleLockScreenShownAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(HandleLockScreenDismissed,
+               bool(brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(HandleLockScreenDismissedAsync,
+               void(const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(RestartJob,
+               bool(const dbus::FileDescriptor& /*in_cred_fd*/,
+                    const std::vector<std::string>& /*in_argv*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(RestartJobAsync,
+               void(const dbus::FileDescriptor& /*in_cred_fd*/,
+                    const std::vector<std::string>& /*in_argv*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(StartDeviceWipe,
+               bool(bool* /*out_done*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(StartDeviceWipeAsync,
+               void(const base::Callback<void(bool /*done*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(SetFlagsForUser,
+               bool(const std::string& /*in_user_email*/,
+                    const std::vector<std::string>& /*in_flags*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD5(SetFlagsForUserAsync,
+               void(const std::string& /*in_user_email*/,
+                    const std::vector<std::string>& /*in_flags*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetServerBackedStateKeys,
+               bool(std::vector<std::vector<uint8_t>>* /*out_state_keys*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(GetServerBackedStateKeysAsync,
+               void(const base::Callback<void(const std::vector<std::vector<uint8_t>>& /*state_keys*/)>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD3(InitMachineInfo,
+               bool(const std::string& /*in_data*/,
+                    brillo::ErrorPtr* /*error*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD4(InitMachineInfoAsync,
+               void(const std::string& /*in_data*/,
+                    const base::Callback<void()>& /*success_callback*/,
+                    const base::Callback<void(brillo::Error*)>& /*error_callback*/,
+                    int /*timeout_ms*/));
+  MOCK_METHOD2(RegisterLoginPromptVisibleSignalHandler,
+               void(const base::Closure& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterSessionStateChangedSignalHandler,
+               void(const base::Callback<void(const std::string&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterSetOwnerKeyCompleteSignalHandler,
+               void(const base::Callback<void(const std::string&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterPropertyChangeCompleteSignalHandler,
+               void(const base::Callback<void(const std::string&)>& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterScreenIsLockedSignalHandler,
+               void(const base::Closure& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+  MOCK_METHOD2(RegisterScreenIsUnlockedSignalHandler,
+               void(const base::Closure& /*signal_callback*/,
+                    dbus::ObjectProxy::OnConnectedCallback /*on_connected_callback*/));
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(SessionManagerInterfaceProxyMock);
+};
+}  // namespace chromium
+}  // namespace org
+
+#endif  // ____CHROMEOS_DBUS_BINDING____________________BUILD_LINK_VAR_CACHE_PORTAGE_CHROMEOS_BASE_CHROMEOS_LOGIN_OUT_DEFAULT_GEN_INCLUDE_SESSION_MANAGER_DBUS_PROXY_MOCKS_H
diff --git a/include/update_engine/dbus-constants.h b/include/update_engine/dbus-constants.h
new file mode 100644
index 0000000..94e35f1
--- /dev/null
+++ b/include/update_engine/dbus-constants.h
@@ -0,0 +1,51 @@
+// Copyright 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef SYSTEM_API_DBUS_UPDATE_ENGINE_DBUS_CONSTANTS_H_
+#define SYSTEM_API_DBUS_UPDATE_ENGINE_DBUS_CONSTANTS_H_
+
+namespace update_engine {
+const char kUpdateEngineInterface[] = "org.chromium.UpdateEngineInterface";
+const char kUpdateEngineServicePath[] = "/org/chromium/UpdateEngine";
+const char kUpdateEngineServiceName[] = "org.chromium.UpdateEngine";
+
+// Generic UpdateEngine D-Bus error.
+static const char* const kUpdateEngineServiceErrorFailed =
+    "org.chromium.UpdateEngine.Error.Failed";
+
+// Methods.
+const char kAttemptUpdate[] = "AttemptUpdate";
+const char kGetStatus[] = "GetStatus";
+const char kRebootIfNeeded[] = "RebootIfNeeded";
+const char kSetChannel[] = "SetChannel";
+const char kGetChannel[] = "GetChannel";
+const char kAttemptRollback[] = "AttemptRollback";
+const char kCanRollback[] = "CanRollback";
+
+// Signals.
+const char kStatusUpdate[] = "StatusUpdate";
+
+// Flags used in the AttemptUpdateWithFlags() D-Bus method.
+typedef enum {
+  kAttemptUpdateFlagNonInteractive = (1<<0)
+} AttemptUpdateFlags;
+
+// Operations contained in StatusUpdate signals.
+const char kUpdateStatusIdle[] = "UPDATE_STATUS_IDLE";
+const char kUpdateStatusCheckingForUpdate[] =
+    "UPDATE_STATUS_CHECKING_FOR_UPDATE";
+const char kUpdateStatusUpdateAvailable[] = "UPDATE_STATUS_UPDATE_AVAILABLE";
+const char kUpdateStatusDownloading[] = "UPDATE_STATUS_DOWNLOADING";
+const char kUpdateStatusVerifying[] = "UPDATE_STATUS_VERIFYING";
+const char kUpdateStatusFinalizing[] = "UPDATE_STATUS_FINALIZING";
+const char kUpdateStatusUpdatedNeedReboot[] =
+    "UPDATE_STATUS_UPDATED_NEED_REBOOT";
+const char kUpdateStatusReportingErrorEvent[] =
+    "UPDATE_STATUS_REPORTING_ERROR_EVENT";
+const char kUpdateStatusAttemptingRollback[] =
+    "UPDATE_STATUS_ATTEMPTING_ROLLBACK";
+const char kUpdateStatusDisabled[] = "UPDATE_STATUS_DISABLED";
+}  // namespace update_engine
+
+#endif  // SYSTEM_API_DBUS_UPDATE_ENGINE_DBUS_CONSTANTS_H_
diff --git a/init/update-engine.conf b/init/update-engine.conf
new file mode 100644
index 0000000..4c05cf4
--- /dev/null
+++ b/init/update-engine.conf
@@ -0,0 +1,39 @@
+#
+# Copyright (C) 2012 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.
+#
+
+description     "System software update service"
+author          "chromium-os-dev@chromium.org"
+
+# N.B. The chromeos-factoryinstall ebuild edits the 'start on' line so as
+# to disable update_engine in factory images.  Do not change this without
+# also updating that reference.
+start on starting system-services
+stop on stopping system-services
+respawn
+
+expect fork
+
+# Runs the daemon at low/idle IO priority so that updates don't
+# impact system responsiveness.
+exec ionice -c3 update_engine
+
+# Put update_engine process in its own cgroup.
+# Default cpu.shares is 1024.
+post-start script
+  cgroup_dir="/sys/fs/cgroup/cpu/${UPSTART_JOB}"
+  mkdir -p "${cgroup_dir}"
+  echo $(status | cut -f 4 -d ' ') > "${cgroup_dir}/tasks"
+end script
diff --git a/libcros_proxy.cc b/libcros_proxy.cc
new file mode 100644
index 0000000..689ed39
--- /dev/null
+++ b/libcros_proxy.cc
@@ -0,0 +1,57 @@
+//
+// Copyright (C) 2015 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 "update_engine/libcros_proxy.h"
+
+using org::chromium::LibCrosServiceInterfaceProxy;
+using org::chromium::LibCrosServiceInterfaceProxyInterface;
+using org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxy;
+using org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface;
+
+namespace {
+const char kLibCrosServiceName[] = "org.chromium.LibCrosService";
+}  // namespace
+
+namespace chromeos_update_engine {
+
+LibCrosProxy::LibCrosProxy(
+    std::unique_ptr<LibCrosServiceInterfaceProxyInterface>
+        service_interface_proxy,
+    std::unique_ptr<UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface>
+        ue_proxy_resolved_interface)
+    : service_interface_proxy_(std::move(service_interface_proxy)),
+      ue_proxy_resolved_interface_(std::move(ue_proxy_resolved_interface)) {
+}
+
+LibCrosProxy::LibCrosProxy(const scoped_refptr<dbus::Bus>& bus)
+    : service_interface_proxy_(
+          new LibCrosServiceInterfaceProxy(bus, kLibCrosServiceName)),
+      ue_proxy_resolved_interface_(
+          new UpdateEngineLibcrosProxyResolvedInterfaceProxy(
+              bus,
+              kLibCrosServiceName)) {
+}
+
+LibCrosServiceInterfaceProxyInterface* LibCrosProxy::service_interface_proxy() {
+  return service_interface_proxy_.get();
+}
+
+UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface*
+LibCrosProxy::ue_proxy_resolved_interface() {
+  return ue_proxy_resolved_interface_.get();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/libcros_proxy.h b/libcros_proxy.h
new file mode 100644
index 0000000..afb5d54
--- /dev/null
+++ b/libcros_proxy.h
@@ -0,0 +1,62 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_LIBCROS_PROXY_H_
+#define UPDATE_ENGINE_LIBCROS_PROXY_H_
+
+#include <memory>
+
+#include <base/macros.h>
+#include <dbus/bus.h>
+
+#include "libcros/dbus-proxies.h"
+
+namespace chromeos_update_engine {
+
+// This class handles the DBus connection with chrome to resolve proxies. This
+// is a thin class to just hold the generated proxies (real or mocked ones).
+class LibCrosProxy final {
+ public:
+  explicit LibCrosProxy(const scoped_refptr<dbus::Bus>& bus);
+  LibCrosProxy(
+      std::unique_ptr<org::chromium::LibCrosServiceInterfaceProxyInterface>
+          service_interface_proxy,
+      std::unique_ptr<
+          org::chromium::
+              UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface>
+          ue_proxy_resolved_interface);
+
+  ~LibCrosProxy() = default;
+
+  // Getters for the two proxies.
+  org::chromium::LibCrosServiceInterfaceProxyInterface*
+  service_interface_proxy();
+  org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface*
+  ue_proxy_resolved_interface();
+
+ private:
+  std::unique_ptr<org::chromium::LibCrosServiceInterfaceProxyInterface>
+      service_interface_proxy_;
+  std::unique_ptr<
+      org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxyInterface>
+      ue_proxy_resolved_interface_;
+
+  DISALLOW_COPY_AND_ASSIGN(LibCrosProxy);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_LIBCROS_PROXY_H_
diff --git a/libupdate_engine-client-test.pc.in b/libupdate_engine-client-test.pc.in
new file mode 100644
index 0000000..92a4af3
--- /dev/null
+++ b/libupdate_engine-client-test.pc.in
@@ -0,0 +1,6 @@
+include_dir=@INCLUDE_DIR@
+
+Name: libupdate_engine-client-test
+Version: 1.0
+Description: update_engine client interface mock library
+Cflags: -I${include_dir}
diff --git a/libupdate_engine-client.pc.in b/libupdate_engine-client.pc.in
new file mode 100644
index 0000000..4c87e1d
--- /dev/null
+++ b/libupdate_engine-client.pc.in
@@ -0,0 +1,6 @@
+include_dir=@INCLUDE_DIR@
+
+Name: libupdate_engine-client
+Version: 1.0
+Description: update_engine client interface library
+Cflags: -I${include_dir}
diff --git a/local_coverage_rate b/local_coverage_rate
new file mode 100755
index 0000000..b189806
--- /dev/null
+++ b/local_coverage_rate
@@ -0,0 +1,101 @@
+#!/bin/bash
+
+#
+# Copyright (C) 2009 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.
+#
+
+# Calculates the test-coverage percentage for non-test files in the
+# update_engine directory. Requires a file 'app.info' to contain the
+# results of running the unittests while collecting coverage data.
+
+cat app.info | awk -F '[,:]' '
+
+BEGIN { OFS = ":"; }
+
+/^SF:/{ FILEN = $2; }
+
+/^end_of_record$/{ FILEN = ""; }
+
+/^DA:/{ print FILEN, $2, $3; }
+
+' | sort | awk -F : '
+BEGIN {
+  OFS = ":";
+  FILEN = "";
+  LINE = "";
+  HITS = 0;
+}
+{
+  NEWFILEN = $1;
+  NEWLINE = $2;
+  if ((NEWFILEN == FILEN) && (NEWLINE == LINE)) {
+    HITS += $3
+  } else {
+    if (FILEN != "") {
+      print FILEN, LINE, HITS;
+    }
+    FILEN = NEWFILEN;
+    LINE = NEWLINE;
+    HITS = $3;
+  }
+}
+' | grep '^.*\/trunk\/src\/platform\/update_engine\/' | \
+fgrep -v '_unittest.cc:' | \
+fgrep -v '/test_utils.' | \
+fgrep -v '/test_http_server.cc' | \
+fgrep -v '/testrunner.cc' | \
+fgrep -v '/mock' | \
+fgrep -v '.pb.cc' | \
+awk -F : '
+
+function printfile() {
+  if (FNAME != "")
+    printf "%-40s %4d / %4d: %5.1f%%\n", FNAME, FILE_GOOD_LINES,
+        (FILE_BAD_LINES + FILE_GOOD_LINES),
+        (FILE_GOOD_LINES * 100) / (FILE_BAD_LINES + FILE_GOOD_LINES);
+}
+
+BEGIN {
+  FNAME = "";
+  FILE_BAD_LINES = 0;
+  FILE_GOOD_LINES = 0;
+}
+{
+  // calc filename
+  ARR_SIZE = split($1, PARTS, "/");
+  NEWFNAME = PARTS[ARR_SIZE];
+  if (NEWFNAME != FNAME) {
+    printfile();
+    FILE_BAD_LINES = 0;
+    FILE_GOOD_LINES = 0;
+    FNAME = NEWFNAME;
+  }
+  if ($3 == "0") {
+    BAD_LINES += 1;
+    FILE_BAD_LINES += 1;
+  } else {
+    GOOD_LINES += 1;
+    FILE_GOOD_LINES += 1;
+  }
+}
+
+END {
+  printfile();
+  print "---\nSummary: tested " GOOD_LINES " / " (BAD_LINES + GOOD_LINES);
+  printf(
+    "Test coverage: %.1f%%\n",
+    ((GOOD_LINES * 100) / (BAD_LINES + GOOD_LINES)));
+}
+'
diff --git a/main.cc b/main.cc
new file mode 100644
index 0000000..8e88f23
--- /dev/null
+++ b/main.cc
@@ -0,0 +1,132 @@
+//
+// Copyright (C) 2012 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 <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+#include <xz.h>
+
+#include <string>
+
+#include <base/at_exit.h>
+#include <base/command_line.h>
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/flag_helper.h>
+#include <brillo/message_loops/base_message_loop.h>
+
+#include "update_engine/common/terminator.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/daemon.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+namespace {
+
+void SetupLogSymlink(const string& symlink_path, const string& log_path) {
+  // TODO(petkov): To ensure a smooth transition between non-timestamped and
+  // timestamped logs, move an existing log to start the first timestamped
+  // one. This code can go away once all clients are switched to this version or
+  // we stop caring about the old-style logs.
+  if (utils::FileExists(symlink_path.c_str()) &&
+      !utils::IsSymlink(symlink_path.c_str())) {
+    base::ReplaceFile(base::FilePath(symlink_path),
+                      base::FilePath(log_path),
+                      nullptr);
+  }
+  base::DeleteFile(base::FilePath(symlink_path), true);
+  if (symlink(log_path.c_str(), symlink_path.c_str()) == -1) {
+    PLOG(ERROR) << "Unable to create symlink " << symlink_path
+                << " pointing at " << log_path;
+  }
+}
+
+string GetTimeAsString(time_t utime) {
+  struct tm tm;
+  CHECK_EQ(localtime_r(&utime, &tm), &tm);
+  char str[16];
+  CHECK_EQ(strftime(str, sizeof(str), "%Y%m%d-%H%M%S", &tm), 15u);
+  return str;
+}
+
+string SetupLogFile(const string& kLogsRoot) {
+  const string kLogSymlink = kLogsRoot + "/update_engine.log";
+  const string kLogsDir = kLogsRoot + "/update_engine";
+  const string kLogPath =
+      base::StringPrintf("%s/update_engine.%s",
+                         kLogsDir.c_str(),
+                         GetTimeAsString(::time(nullptr)).c_str());
+  mkdir(kLogsDir.c_str(), 0755);
+  SetupLogSymlink(kLogSymlink, kLogPath);
+  return kLogSymlink;
+}
+
+void SetupLogging(bool log_to_std_err) {
+  string log_file;
+  logging::LoggingSettings log_settings;
+  log_settings.lock_log = logging::DONT_LOCK_LOG_FILE;
+  log_settings.delete_old = logging::APPEND_TO_OLD_LOG_FILE;
+
+  if (log_to_std_err) {
+    // Log to stderr initially.
+    log_settings.log_file = nullptr;
+    log_settings.logging_dest = logging::LOG_TO_SYSTEM_DEBUG_LOG;
+  } else {
+    log_file = SetupLogFile("/var/log");
+    log_settings.log_file = log_file.c_str();
+    log_settings.logging_dest = logging::LOG_TO_FILE;
+  }
+
+  logging::InitLogging(log_settings);
+}
+
+}  // namespace
+}  // namespace chromeos_update_engine
+
+int main(int argc, char** argv) {
+  DEFINE_bool(logtostderr, false,
+              "Write logs to stderr instead of to a file in log_dir.");
+  DEFINE_bool(foreground, false,
+              "Don't daemon()ize; run in foreground.");
+
+  chromeos_update_engine::Terminator::Init();
+  brillo::FlagHelper::Init(argc, argv, "Chromium OS Update Engine");
+  chromeos_update_engine::SetupLogging(FLAGS_logtostderr);
+  if (!FLAGS_foreground)
+    PLOG_IF(FATAL, daemon(0, 0) == 1) << "daemon() failed";
+
+  LOG(INFO) << "Chrome OS Update Engine starting";
+
+  // xz-embedded requires to initialize its CRC-32 table once on startup.
+  xz_crc32_init();
+
+  // Ensure that all written files have safe permissions.
+  // This is a mask, so we _block_ all permissions for the group owner and other
+  // users but allow all permissions for the user owner. We allow execution
+  // for the owner so we can create directories.
+  // Done _after_ log file creation.
+  umask(S_IRWXG | S_IRWXO);
+
+  chromeos_update_engine::UpdateEngineDaemon update_engine_daemon;
+  int exit_code = update_engine_daemon.Run();
+
+  LOG(INFO) << "Chrome OS Update Engine terminating with exit code "
+            << exit_code;
+  return exit_code;
+}
diff --git a/metrics.cc b/metrics.cc
new file mode 100644
index 0000000..742ba7e
--- /dev/null
+++ b/metrics.cc
@@ -0,0 +1,526 @@
+//
+// Copyright (C) 2014 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 "update_engine/metrics.h"
+
+#include <string>
+
+#include <base/logging.h>
+#include <metrics/metrics_library.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/metrics_utils.h"
+#include "update_engine/system_state.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace metrics {
+
+// UpdateEngine.Daily.* metrics.
+const char kMetricDailyOSAgeDays[] = "UpdateEngine.Daily.OSAgeDays";
+
+// UpdateEngine.Check.* metrics.
+const char kMetricCheckDownloadErrorCode[] =
+    "UpdateEngine.Check.DownloadErrorCode";
+const char kMetricCheckReaction[] = "UpdateEngine.Check.Reaction";
+const char kMetricCheckResult[] = "UpdateEngine.Check.Result";
+const char kMetricCheckTimeSinceLastCheckMinutes[] =
+    "UpdateEngine.Check.TimeSinceLastCheckMinutes";
+const char kMetricCheckTimeSinceLastCheckUptimeMinutes[] =
+    "UpdateEngine.Check.TimeSinceLastCheckUptimeMinutes";
+
+// UpdateEngine.Attempt.* metrics.
+const char kMetricAttemptNumber[] = "UpdateEngine.Attempt.Number";
+const char kMetricAttemptPayloadType[] =
+    "UpdateEngine.Attempt.PayloadType";
+const char kMetricAttemptPayloadSizeMiB[] =
+    "UpdateEngine.Attempt.PayloadSizeMiB";
+const char kMetricAttemptConnectionType[] =
+    "UpdateEngine.Attempt.ConnectionType";
+const char kMetricAttemptDurationMinutes[] =
+    "UpdateEngine.Attempt.DurationMinutes";
+const char kMetricAttemptDurationUptimeMinutes[] =
+    "UpdateEngine.Attempt.DurationUptimeMinutes";
+const char kMetricAttemptTimeSinceLastAttemptMinutes[] =
+    "UpdateEngine.Attempt.TimeSinceLastAttemptMinutes";
+const char kMetricAttemptTimeSinceLastAttemptUptimeMinutes[] =
+    "UpdateEngine.Attempt.TimeSinceLastAttemptUptimeMinutes";
+const char kMetricAttemptPayloadBytesDownloadedMiB[] =
+    "UpdateEngine.Attempt.PayloadBytesDownloadedMiB";
+const char kMetricAttemptPayloadDownloadSpeedKBps[] =
+    "UpdateEngine.Attempt.PayloadDownloadSpeedKBps";
+const char kMetricAttemptDownloadSource[] =
+    "UpdateEngine.Attempt.DownloadSource";
+const char kMetricAttemptResult[] =
+    "UpdateEngine.Attempt.Result";
+const char kMetricAttemptInternalErrorCode[] =
+    "UpdateEngine.Attempt.InternalErrorCode";
+const char kMetricAttemptDownloadErrorCode[] =
+    "UpdateEngine.Attempt.DownloadErrorCode";
+
+// UpdateEngine.SuccessfulUpdate.* metrics.
+const char kMetricSuccessfulUpdateAttemptCount[] =
+    "UpdateEngine.SuccessfulUpdate.AttemptCount";
+const char kMetricSuccessfulUpdateBytesDownloadedMiB[] =
+    "UpdateEngine.SuccessfulUpdate.BytesDownloadedMiB";
+const char kMetricSuccessfulUpdateDownloadOverheadPercentage[] =
+    "UpdateEngine.SuccessfulUpdate.DownloadOverheadPercentage";
+const char kMetricSuccessfulUpdateDownloadSourcesUsed[] =
+    "UpdateEngine.SuccessfulUpdate.DownloadSourcesUsed";
+const char kMetricSuccessfulUpdatePayloadType[] =
+    "UpdateEngine.SuccessfulUpdate.PayloadType";
+const char kMetricSuccessfulUpdatePayloadSizeMiB[] =
+    "UpdateEngine.SuccessfulUpdate.PayloadSizeMiB";
+const char kMetricSuccessfulUpdateRebootCount[] =
+    "UpdateEngine.SuccessfulUpdate.RebootCount";
+const char kMetricSuccessfulUpdateTotalDurationMinutes[] =
+    "UpdateEngine.SuccessfulUpdate.TotalDurationMinutes";
+const char kMetricSuccessfulUpdateUpdatesAbandonedCount[] =
+    "UpdateEngine.SuccessfulUpdate.UpdatesAbandonedCount";
+const char kMetricSuccessfulUpdateUrlSwitchCount[] =
+    "UpdateEngine.SuccessfulUpdate.UrlSwitchCount";
+
+// UpdateEngine.Rollback.* metric.
+const char kMetricRollbackResult[] = "UpdateEngine.Rollback.Result";
+
+// UpdateEngine.CertificateCheck.* metrics.
+const char kMetricCertificateCheckUpdateCheck[] =
+    "UpdateEngine.CertificateCheck.UpdateCheck";
+const char kMetricCertificateCheckDownload[] =
+    "UpdateEngine.CertificateCheck.Download";
+
+// UpdateEngine.* metrics.
+const char kMetricFailedUpdateCount[] = "UpdateEngine.FailedUpdateCount";
+const char kMetricInstallDateProvisioningSource[] =
+    "UpdateEngine.InstallDateProvisioningSource";
+const char kMetricTimeToRebootMinutes[] =
+    "UpdateEngine.TimeToRebootMinutes";
+
+void ReportDailyMetrics(SystemState *system_state,
+                        base::TimeDelta os_age) {
+  string metric = metrics::kMetricDailyOSAgeDays;
+  LOG(INFO) << "Uploading " << utils::FormatTimeDelta(os_age)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(
+      metric,
+      static_cast<int>(os_age.InDays()),
+      0,     // min: 0 days
+      6*30,  // max: 6 months (approx)
+      50);   // num_buckets
+}
+
+void ReportUpdateCheckMetrics(SystemState *system_state,
+                              CheckResult result,
+                              CheckReaction reaction,
+                              DownloadErrorCode download_error_code) {
+  string metric;
+  int value;
+  int max_value;
+
+  if (result != metrics::CheckResult::kUnset) {
+    metric = metrics::kMetricCheckResult;
+    value = static_cast<int>(result);
+    max_value = static_cast<int>(metrics::CheckResult::kNumConstants) - 1;
+    LOG(INFO) << "Sending " << value << " for metric " << metric << " (enum)";
+    system_state->metrics_lib()->SendEnumToUMA(metric, value, max_value);
+  }
+  if (reaction != metrics::CheckReaction::kUnset) {
+    metric = metrics::kMetricCheckReaction;
+    value = static_cast<int>(reaction);
+    max_value = static_cast<int>(metrics::CheckReaction::kNumConstants) - 1;
+    LOG(INFO) << "Sending " << value << " for metric " << metric << " (enum)";
+    system_state->metrics_lib()->SendEnumToUMA(metric, value, max_value);
+  }
+  if (download_error_code != metrics::DownloadErrorCode::kUnset) {
+    metric = metrics::kMetricCheckDownloadErrorCode;
+    value = static_cast<int>(download_error_code);
+    LOG(INFO) << "Sending " << value << " for metric " << metric << " (sparse)";
+    system_state->metrics_lib()->SendSparseToUMA(metric, value);
+  }
+
+  base::TimeDelta time_since_last;
+  if (metrics_utils::WallclockDurationHelper(
+          system_state,
+          kPrefsMetricsCheckLastReportingTime,
+          &time_since_last)) {
+    metric = kMetricCheckTimeSinceLastCheckMinutes;
+    LOG(INFO) << "Sending " << utils::FormatTimeDelta(time_since_last)
+              << " for metric " << metric;
+    system_state->metrics_lib()->SendToUMA(
+        metric,
+        time_since_last.InMinutes(),
+        0,         // min: 0 min
+        30*24*60,  // max: 30 days
+        50);       // num_buckets
+  }
+
+  base::TimeDelta uptime_since_last;
+  static int64_t uptime_since_last_storage = 0;
+  if (metrics_utils::MonotonicDurationHelper(system_state,
+                                             &uptime_since_last_storage,
+                                             &uptime_since_last)) {
+    metric = kMetricCheckTimeSinceLastCheckUptimeMinutes;
+    LOG(INFO) << "Sending " << utils::FormatTimeDelta(uptime_since_last)
+              << " for metric " << metric;
+    system_state->metrics_lib()->SendToUMA(
+        metric,
+        uptime_since_last.InMinutes(),
+        0,         // min: 0 min
+        30*24*60,  // max: 30 days
+        50);       // num_buckets
+  }
+}
+
+void ReportAbnormallyTerminatedUpdateAttemptMetrics(
+    SystemState *system_state) {
+
+  string metric = metrics::kMetricAttemptResult;
+  AttemptResult attempt_result = AttemptResult::kAbnormalTermination;
+
+  LOG(INFO) << "Uploading " << static_cast<int>(attempt_result)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric,
+      static_cast<int>(attempt_result),
+      static_cast<int>(AttemptResult::kNumConstants));
+}
+
+void ReportUpdateAttemptMetrics(
+    SystemState *system_state,
+    int attempt_number,
+    PayloadType payload_type,
+    base::TimeDelta duration,
+    base::TimeDelta duration_uptime,
+    int64_t payload_size,
+    int64_t payload_bytes_downloaded,
+    int64_t payload_download_speed_bps,
+    DownloadSource download_source,
+    AttemptResult attempt_result,
+    ErrorCode internal_error_code,
+    DownloadErrorCode payload_download_error_code,
+    ConnectionType connection_type) {
+  string metric;
+
+  metric = metrics::kMetricAttemptNumber;
+  LOG(INFO) << "Uploading " << attempt_number << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         attempt_number,
+                                         0,    // min: 0 attempts
+                                         49,   // max: 49 attempts
+                                         50);  // num_buckets
+
+  metric = metrics::kMetricAttemptPayloadType;
+  LOG(INFO) << "Uploading " << utils::ToString(payload_type)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendEnumToUMA(metric,
+                                             payload_type,
+                                             kNumPayloadTypes);
+
+  metric = metrics::kMetricAttemptDurationMinutes;
+  LOG(INFO) << "Uploading " << utils::FormatTimeDelta(duration)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         duration.InMinutes(),
+                                         0,         // min: 0 min
+                                         10*24*60,  // max: 10 days
+                                         50);       // num_buckets
+
+  metric = metrics::kMetricAttemptDurationUptimeMinutes;
+  LOG(INFO) << "Uploading " << utils::FormatTimeDelta(duration_uptime)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         duration_uptime.InMinutes(),
+                                         0,         // min: 0 min
+                                         10*24*60,  // max: 10 days
+                                         50);       // num_buckets
+
+  metric = metrics::kMetricAttemptPayloadSizeMiB;
+  int64_t payload_size_mib = payload_size / kNumBytesInOneMiB;
+  LOG(INFO) << "Uploading " << payload_size_mib << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         payload_size_mib,
+                                         0,     // min: 0 MiB
+                                         1024,  // max: 1024 MiB = 1 GiB
+                                         50);   // num_buckets
+
+  metric = metrics::kMetricAttemptPayloadBytesDownloadedMiB;
+  int64_t payload_bytes_downloaded_mib =
+       payload_bytes_downloaded / kNumBytesInOneMiB;
+  LOG(INFO) << "Uploading " << payload_bytes_downloaded_mib
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         payload_bytes_downloaded_mib,
+                                         0,     // min: 0 MiB
+                                         1024,  // max: 1024 MiB = 1 GiB
+                                         50);   // num_buckets
+
+  metric = metrics::kMetricAttemptPayloadDownloadSpeedKBps;
+  int64_t payload_download_speed_kbps = payload_download_speed_bps / 1000;
+  LOG(INFO) << "Uploading " << payload_download_speed_kbps
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         payload_download_speed_kbps,
+                                         0,        // min: 0 kB/s
+                                         10*1000,  // max: 10000 kB/s = 10 MB/s
+                                         50);      // num_buckets
+
+  metric = metrics::kMetricAttemptDownloadSource;
+  LOG(INFO) << "Uploading " << download_source
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendEnumToUMA(metric,
+                                             download_source,
+                                             kNumDownloadSources);
+
+  metric = metrics::kMetricAttemptResult;
+  LOG(INFO) << "Uploading " << static_cast<int>(attempt_result)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric,
+      static_cast<int>(attempt_result),
+      static_cast<int>(AttemptResult::kNumConstants));
+
+  if (internal_error_code != ErrorCode::kSuccess) {
+    metric = metrics::kMetricAttemptInternalErrorCode;
+    LOG(INFO) << "Uploading " << internal_error_code
+              << " for metric " <<  metric;
+    system_state->metrics_lib()->SendEnumToUMA(
+        metric,
+        static_cast<int>(internal_error_code),
+        static_cast<int>(ErrorCode::kUmaReportedMax));
+  }
+
+  if (payload_download_error_code != DownloadErrorCode::kUnset) {
+    metric = metrics::kMetricAttemptDownloadErrorCode;
+    LOG(INFO) << "Uploading " << static_cast<int>(payload_download_error_code)
+              << " for metric " <<  metric << " (sparse)";
+    system_state->metrics_lib()->SendSparseToUMA(
+        metric,
+        static_cast<int>(payload_download_error_code));
+  }
+
+  base::TimeDelta time_since_last;
+  if (metrics_utils::WallclockDurationHelper(
+          system_state,
+          kPrefsMetricsAttemptLastReportingTime,
+          &time_since_last)) {
+    metric = kMetricAttemptTimeSinceLastAttemptMinutes;
+    LOG(INFO) << "Sending " << utils::FormatTimeDelta(time_since_last)
+              << " for metric " << metric;
+    system_state->metrics_lib()->SendToUMA(
+        metric,
+        time_since_last.InMinutes(),
+        0,         // min: 0 min
+        30*24*60,  // max: 30 days
+        50);       // num_buckets
+  }
+
+  static int64_t uptime_since_last_storage = 0;
+  base::TimeDelta uptime_since_last;
+  if (metrics_utils::MonotonicDurationHelper(system_state,
+                                             &uptime_since_last_storage,
+                                             &uptime_since_last)) {
+    metric = kMetricAttemptTimeSinceLastAttemptUptimeMinutes;
+    LOG(INFO) << "Sending " << utils::FormatTimeDelta(uptime_since_last)
+              << " for metric " << metric;
+    system_state->metrics_lib()->SendToUMA(
+        metric,
+        uptime_since_last.InMinutes(),
+        0,         // min: 0 min
+        30*24*60,  // max: 30 days
+        50);       // num_buckets
+  }
+
+  metric = metrics::kMetricAttemptConnectionType;
+  LOG(INFO) << "Uploading " << static_cast<int>(connection_type)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric,
+      static_cast<int>(connection_type),
+      static_cast<int>(ConnectionType::kNumConstants));
+}
+
+
+void ReportSuccessfulUpdateMetrics(
+         SystemState *system_state,
+         int attempt_count,
+         int updates_abandoned_count,
+         PayloadType payload_type,
+         int64_t payload_size,
+         int64_t num_bytes_downloaded[kNumDownloadSources],
+         int download_overhead_percentage,
+         base::TimeDelta total_duration,
+         int reboot_count,
+         int url_switch_count) {
+  string metric;
+  int64_t mbs;
+
+  metric = kMetricSuccessfulUpdatePayloadSizeMiB;
+  mbs = payload_size / kNumBytesInOneMiB;
+  LOG(INFO) << "Uploading " << mbs << " (MiBs) for metric " << metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         mbs,
+                                         0,     // min: 0 MiB
+                                         1024,  // max: 1024 MiB = 1 GiB
+                                         50);   // num_buckets
+
+  int64_t total_bytes = 0;
+  int download_sources_used = 0;
+  for (int i = 0; i < kNumDownloadSources + 1; i++) {
+    DownloadSource source = static_cast<DownloadSource>(i);
+
+    // Only consider this download source (and send byte counts) as
+    // having been used if we downloaded a non-trivial amount of bytes
+    // (e.g. at least 1 MiB) that contributed to the
+    // update. Otherwise we're going to end up with a lot of zero-byte
+    // events in the histogram.
+
+    metric = metrics::kMetricSuccessfulUpdateBytesDownloadedMiB;
+    if (i < kNumDownloadSources) {
+      metric += utils::ToString(source);
+      mbs = num_bytes_downloaded[i] / kNumBytesInOneMiB;
+      total_bytes += num_bytes_downloaded[i];
+      if (mbs > 0)
+        download_sources_used |= (1 << i);
+    } else {
+      mbs = total_bytes / kNumBytesInOneMiB;
+    }
+
+    if (mbs > 0) {
+      LOG(INFO) << "Uploading " << mbs << " (MiBs) for metric " << metric;
+      system_state->metrics_lib()->SendToUMA(metric,
+                                             mbs,
+                                             0,     // min: 0 MiB
+                                             1024,  // max: 1024 MiB = 1 GiB
+                                             50);   // num_buckets
+    }
+  }
+
+  metric = metrics::kMetricSuccessfulUpdateDownloadSourcesUsed;
+  LOG(INFO) << "Uploading 0x" << std::hex << download_sources_used
+            << " (bit flags) for metric " << metric;
+  system_state->metrics_lib()->SendToUMA(
+      metric,
+      download_sources_used,
+      0,                               // min
+      (1 << kNumDownloadSources) - 1,  // max
+      1 << kNumDownloadSources);       // num_buckets
+
+  metric = metrics::kMetricSuccessfulUpdateDownloadOverheadPercentage;
+  LOG(INFO) << "Uploading " << download_overhead_percentage
+            << "% for metric " << metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         download_overhead_percentage,
+                                         0,     // min: 0% overhead
+                                         1000,  // max: 1000% overhead
+                                         50);   // num_buckets
+
+  metric = metrics::kMetricSuccessfulUpdateUrlSwitchCount;
+  LOG(INFO) << "Uploading " << url_switch_count
+            << " (count) for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         url_switch_count,
+                                         0,    // min: 0 URL switches
+                                         49,   // max: 49 URL switches
+                                         50);  // num_buckets
+
+  metric = metrics::kMetricSuccessfulUpdateTotalDurationMinutes;
+  LOG(INFO) << "Uploading " << utils::FormatTimeDelta(total_duration)
+            << " for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(
+       metric,
+       static_cast<int>(total_duration.InMinutes()),
+       0,          // min: 0 min
+       365*24*60,  // max: 365 days ~= 1 year
+       50);        // num_buckets
+
+  metric = metrics::kMetricSuccessfulUpdateRebootCount;
+  LOG(INFO) << "Uploading reboot count of " << reboot_count << " for metric "
+            <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         reboot_count,
+                                         0,    // min: 0 reboots
+                                         49,   // max: 49 reboots
+                                         50);  // num_buckets
+
+  metric = metrics::kMetricSuccessfulUpdatePayloadType;
+  system_state->metrics_lib()->SendEnumToUMA(metric,
+                                             payload_type,
+                                             kNumPayloadTypes);
+  LOG(INFO) << "Uploading " << utils::ToString(payload_type)
+            << " for metric " <<  metric;
+
+  metric = metrics::kMetricSuccessfulUpdateAttemptCount;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         attempt_count,
+                                         1,    // min: 1 attempt
+                                         50,   // max: 50 attempts
+                                         50);  // num_buckets
+  LOG(INFO) << "Uploading " << attempt_count
+            << " for metric " <<  metric;
+
+  metric = metrics::kMetricSuccessfulUpdateUpdatesAbandonedCount;
+  LOG(INFO) << "Uploading " << updates_abandoned_count
+            << " (count) for metric " <<  metric;
+  system_state->metrics_lib()->SendToUMA(metric,
+                                         updates_abandoned_count,
+                                         0,    // min: 0 counts
+                                         49,   // max: 49 counts
+                                         50);  // num_buckets
+}
+
+void ReportRollbackMetrics(SystemState *system_state,
+                           RollbackResult result) {
+  string metric;
+  int value;
+
+  metric = metrics::kMetricRollbackResult;
+  value = static_cast<int>(result);
+  LOG(INFO) << "Sending " << value << " for metric " << metric << " (enum)";
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric,
+      value,
+      static_cast<int>(metrics::RollbackResult::kNumConstants));
+}
+
+void ReportCertificateCheckMetrics(SystemState* system_state,
+                                   ServerToCheck server_to_check,
+                                   CertificateCheckResult result) {
+  string metric;
+  switch (server_to_check) {
+    case ServerToCheck::kUpdate:
+      metric = kMetricCertificateCheckUpdateCheck;
+      break;
+    case ServerToCheck::kDownload:
+      metric = kMetricCertificateCheckDownload;
+      break;
+    case ServerToCheck::kNone:
+      return;
+  }
+  LOG(INFO) << "Uploading " << static_cast<int>(result) << " for metric "
+            << metric;
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric, static_cast<int>(result),
+      static_cast<int>(CertificateCheckResult::kNumConstants));
+}
+
+}  // namespace metrics
+
+}  // namespace chromeos_update_engine
diff --git a/metrics.h b/metrics.h
new file mode 100644
index 0000000..ec9d880
--- /dev/null
+++ b/metrics.h
@@ -0,0 +1,320 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_METRICS_H_
+#define UPDATE_ENGINE_METRICS_H_
+
+#include <base/time/time.h>
+
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/error_code.h"
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+namespace metrics {
+
+// UpdateEngine.Daily.* metrics.
+extern const char kMetricDailyOSAgeDays[];
+
+// UpdateEngine.Check.* metrics.
+extern const char kMetricCheckDownloadErrorCode[];
+extern const char kMetricCheckReaction[];
+extern const char kMetricCheckResult[];
+extern const char kMetricCheckTimeSinceLastCheckMinutes[];
+extern const char kMetricCheckTimeSinceLastCheckUptimeMinutes[];
+
+// UpdateEngine.Attempt.* metrics.
+extern const char kMetricAttemptNumber[];
+extern const char kMetricAttemptPayloadType[];
+extern const char kMetricAttemptPayloadSizeMiB[];
+extern const char kMetricAttemptConnectionType[];
+extern const char kMetricAttemptDurationMinutes[];
+extern const char kMetricAttemptDurationUptimeMinutes[];
+extern const char kMetricAttemptTimeSinceLastAttemptSeconds[];
+extern const char kMetricAttemptTimeSinceLastAttemptUptimeSeconds[];
+extern const char kMetricAttemptPayloadBytesDownloaded[];
+extern const char kMetricAttemptPayloadDownloadSpeedKBps[];
+extern const char kMetricAttemptDownloadSource[];
+extern const char kMetricAttemptResult[];
+extern const char kMetricAttemptInternalErrorCode[];
+extern const char kMetricAttemptDownloadErrorCode[];
+
+// UpdateEngine.SuccessfulUpdate.* metrics.
+extern const char kMetricSuccessfulUpdateAttemptCount[];
+extern const char kMetricSuccessfulUpdateBytesDownloadedMiB[];
+extern const char kMetricSuccessfulUpdateDownloadOverheadPercentage[];
+extern const char kMetricSuccessfulUpdateDownloadSourcesUsed[];
+extern const char kMetricSuccessfulUpdatePayloadType[];
+extern const char kMetricSuccessfulUpdatePayloadSizeMiB[];
+extern const char kMetricSuccessfulUpdateTotalDurationMinutes[];
+extern const char kMetricSuccessfulUpdateRebootCount[];
+extern const char kMetricSuccessfulUpdateUpdatesAbandonedCount[];
+extern const char kMetricSuccessfulUpdateUrlSwitchCount[];
+
+// UpdateEngine.Rollback.* metric.
+extern const char kMetricRollbackResult[];
+
+// UpdateEngine.* metrics.
+extern const char kMetricFailedUpdateCount[];
+extern const char kMetricInstallDateProvisioningSource[];
+extern const char kMetricTimeToRebootMinutes[];
+
+// The possible outcomes when checking for updates.
+//
+// This is used in the UpdateEngine.Check.Result histogram.
+enum class CheckResult {
+  kUpdateAvailable,    // Response indicates an update is available.
+  kNoUpdateAvailable,  // Response indicates no updates are available.
+  kDownloadError,      // Error downloading response from Omaha.
+  kParsingError,       // Error parsing response.
+  kRebootPending,      // No update check was performed a reboot is pending.
+
+  kNumConstants,
+  kUnset = -1
+};
+
+// Possible ways a device can react to a new update being available.
+//
+// This is used in the UpdateEngine.Check.Reaction histogram.
+enum class CheckReaction {
+  kUpdating,    // Device proceeds to download and apply update.
+  kIgnored  ,   // Device-policy dictates ignoring the update.
+  kDeferring,   // Device-policy dictates waiting.
+  kBackingOff,  // Previous errors dictates waiting.
+
+  kNumConstants,
+  kUnset = -1
+};
+
+// The possible ways that downloading from a HTTP or HTTPS server can fail.
+//
+// This is used in the UpdateEngine.Check.DownloadErrorCode and
+// UpdateEngine.Attempt.DownloadErrorCode histograms.
+enum class DownloadErrorCode {
+  // Errors that can happen in the field. See http://crbug.com/355745
+  // for how we plan to add more detail in the future.
+  kDownloadError = 0,  // Error downloading data from server.
+
+  // IMPORTANT: When adding a new error code, add at the bottom of the
+  // above block and before the kInputMalformed field. This
+  // is to ensure that error codes are not reordered.
+
+  // This error code is used to convey that malformed input was given
+  // to the utils::GetDownloadErrorCode() function. This should never
+  // happen but if it does it's because of an internal update_engine
+  // error and we're interested in knowing this.
+  kInputMalformed = 100,
+
+  // Bucket for capturing HTTP status codes not in the 200-599
+  // range. This should never happen in practice but if it does we
+  // want to know.
+  kHttpStatusOther = 101,
+
+  // Above 200 and below 600, the value is the HTTP status code.
+  kHttpStatus200 = 200,
+
+  kNumConstants = 600,
+
+  kUnset = -1
+};
+
+// Possible ways an update attempt can end.
+//
+// This is used in the UpdateEngine.Attempt.Result histogram.
+enum class AttemptResult {
+  kUpdateSucceeded,             // The update succeeded.
+  kInternalError,               // An internal error occurred.
+  kPayloadDownloadError,        // Failure while downloading payload.
+  kMetadataMalformed,           // Metadata was malformed.
+  kOperationMalformed,          // An operation was malformed.
+  kOperationExecutionError,     // An operation failed to execute.
+  kMetadataVerificationFailed,  // Metadata verification failed.
+  kPayloadVerificationFailed,   // Payload verification failed.
+  kVerificationFailed,          // Root or Kernel partition verification failed.
+  kPostInstallFailed,           // The postinstall step failed.
+  kAbnormalTermination,         // The attempt ended abnormally.
+
+  kNumConstants,
+
+  kUnset = -1
+};
+
+// Possible ways the device is connected to the Internet.
+//
+// This is used in the UpdateEngine.Attempt.ConnectionType histogram.
+enum class ConnectionType {
+  kUnknown,           // Unknown.
+  kEthernet,          // Ethernet.
+  kWifi,              // Wireless.
+  kWimax,             // WiMax.
+  kBluetooth,         // Bluetooth.
+  kCellular,          // Cellular.
+  kTetheredEthernet,  // Tethered (Ethernet).
+  kTetheredWifi,      // Tethered (Wifi).
+
+  kNumConstants,
+  kUnset = -1
+};
+
+// Possible ways a rollback can end.
+//
+// This is used in the UpdateEngine.Rollback histogram.
+enum class RollbackResult {
+  kFailed,
+  kSuccess,
+
+  kNumConstants
+};
+
+// Helper function to report metrics related to rollback. The
+// following metrics are reported:
+//
+//  |kMetricRollbackResult|
+void ReportRollbackMetrics(SystemState *system_state,
+                           RollbackResult result);
+
+// Helper function to report metrics reported once a day. The
+// following metrics are reported:
+//
+//  |kMetricDailyOSAgeDays|
+void ReportDailyMetrics(SystemState *system_state,
+                        base::TimeDelta os_age);
+
+// Helper function to report metrics after completing an update check
+// with the ChromeOS update server ("Omaha"). The following metrics
+// are reported:
+//
+//  |kMetricCheckResult|
+//  |kMetricCheckReaction|
+//  |kMetricCheckDownloadErrorCode|
+//  |kMetricCheckTimeSinceLastCheckMinutes|
+//  |kMetricCheckTimeSinceLastCheckUptimeMinutes|
+//
+// The |kMetricCheckResult| metric will only be reported if |result|
+// is not |kUnset|.
+//
+// The |kMetricCheckReaction| metric will only be reported if
+// |reaction| is not |kUnset|.
+//
+// The |kMetricCheckDownloadErrorCode| will only be reported if
+// |download_error_code| is not |kUnset|.
+//
+// The values for the |kMetricCheckTimeSinceLastCheckMinutes| and
+// |kMetricCheckTimeSinceLastCheckUptimeMinutes| metrics are
+// automatically reported and calculated by maintaining persistent
+// and process-local state variables.
+void ReportUpdateCheckMetrics(SystemState *system_state,
+                              CheckResult result,
+                              CheckReaction reaction,
+                              DownloadErrorCode download_error_code);
+
+
+// Helper function to report metrics after the completion of each
+// update attempt. The following metrics are reported:
+//
+//  |kMetricAttemptNumber|
+//  |kMetricAttemptPayloadType|
+//  |kMetricAttemptPayloadSizeMiB|
+//  |kMetricAttemptDurationSeconds|
+//  |kMetricAttemptDurationUptimeSeconds|
+//  |kMetricAttemptTimeSinceLastAttemptMinutes|
+//  |kMetricAttemptTimeSinceLastAttemptUptimeMinutes|
+//  |kMetricAttemptPayloadBytesDownloadedMiB|
+//  |kMetricAttemptPayloadDownloadSpeedKBps|
+//  |kMetricAttemptDownloadSource|
+//  |kMetricAttemptResult|
+//  |kMetricAttemptInternalErrorCode|
+//  |kMetricAttemptDownloadErrorCode|
+//
+// The |kMetricAttemptInternalErrorCode| metric will only be reported
+// if |internal_error_code| is not |kErrorSuccess|.
+//
+// The |kMetricAttemptDownloadErrorCode| metric will only be
+// reported if |payload_download_error_code| is not |kUnset|.
+//
+// The values for the |kMetricAttemptTimeSinceLastAttemptMinutes| and
+// |kMetricAttemptTimeSinceLastAttemptUptimeMinutes| metrics are
+// automatically calculated and reported by maintaining persistent and
+// process-local state variables.
+void ReportUpdateAttemptMetrics(
+    SystemState *system_state,
+    int attempt_number,
+    PayloadType payload_type,
+    base::TimeDelta duration,
+    base::TimeDelta duration_uptime,
+    int64_t payload_size,
+    int64_t payload_bytes_downloaded,
+    int64_t payload_download_speed_bps,
+    DownloadSource download_source,
+    AttemptResult attempt_result,
+    ErrorCode internal_error_code,
+    DownloadErrorCode payload_download_error_code,
+    ConnectionType connection_type);
+
+// Reports the |kAbnormalTermination| for the |kMetricAttemptResult|
+// metric. No other metrics in the UpdateEngine.Attempt.* namespace
+// will be reported.
+void ReportAbnormallyTerminatedUpdateAttemptMetrics(SystemState *system_state);
+
+// Helper function to report the after the completion of a successful
+// update attempt. The following metrics are reported:
+//
+//  |kMetricSuccessfulUpdateAttemptCount|
+//  |kMetricSuccessfulUpdateUpdatesAbandonedCount|
+//  |kMetricSuccessfulUpdatePayloadType|
+//  |kMetricSuccessfulUpdatePayloadSizeMiB|
+//  |kMetricSuccessfulUpdateBytesDownloadedMiBHttpsServer|
+//  |kMetricSuccessfulUpdateBytesDownloadedMiBHttpServer|
+//  |kMetricSuccessfulUpdateBytesDownloadedMiBHttpPeer|
+//  |kMetricSuccessfulUpdateBytesDownloadedMiB|
+//  |kMetricSuccessfulUpdateDownloadSourcesUsed|
+//  |kMetricSuccessfulUpdateDownloadOverheadPercentage|
+//  |kMetricSuccessfulUpdateTotalDurationMinutes|
+//  |kMetricSuccessfulUpdateRebootCount|
+//  |kMetricSuccessfulUpdateUrlSwitchCount|
+//
+// The values for the |kMetricSuccessfulUpdateDownloadSourcesUsed| are
+// |kMetricSuccessfulUpdateBytesDownloadedMiB| metrics automatically
+// calculated from examining the |num_bytes_downloaded| array.
+void ReportSuccessfulUpdateMetrics(
+    SystemState *system_state,
+    int attempt_count,
+    int updates_abandoned_count,
+    PayloadType payload_type,
+    int64_t payload_size,
+    int64_t num_bytes_downloaded[kNumDownloadSources],
+    int download_overhead_percentage,
+    base::TimeDelta total_duration,
+    int reboot_count,
+    int url_switch_count);
+
+// Helper function to report the after the completion of a SSL certificate
+// check. One of the following metrics is reported:
+//
+//  |kMetricCertificateCheckUpdateCheck|
+//  |kMetricCertificateCheckDownload|
+void ReportCertificateCheckMetrics(SystemState* system_state,
+                                   ServerToCheck server_to_check,
+                                   CertificateCheckResult result);
+
+}  // namespace metrics
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_METRICS_H_
diff --git a/metrics_utils.cc b/metrics_utils.cc
new file mode 100644
index 0000000..eb99c7d
--- /dev/null
+++ b/metrics_utils.cc
@@ -0,0 +1,301 @@
+//
+// Copyright (C) 2015 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 "update_engine/metrics_utils.h"
+
+#include <string>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/system_state.h"
+
+using base::Time;
+using base::TimeDelta;
+
+namespace chromeos_update_engine {
+namespace metrics_utils {
+
+metrics::AttemptResult GetAttemptResult(ErrorCode code) {
+  ErrorCode base_code = static_cast<ErrorCode>(
+      static_cast<int>(code) & ~static_cast<int>(ErrorCode::kSpecialFlags));
+
+  switch (base_code) {
+    case ErrorCode::kSuccess:
+      return metrics::AttemptResult::kUpdateSucceeded;
+
+    case ErrorCode::kDownloadTransferError:
+      return metrics::AttemptResult::kPayloadDownloadError;
+
+    case ErrorCode::kDownloadInvalidMetadataSize:
+    case ErrorCode::kDownloadInvalidMetadataMagicString:
+    case ErrorCode::kDownloadMetadataSignatureError:
+    case ErrorCode::kDownloadMetadataSignatureVerificationError:
+    case ErrorCode::kPayloadMismatchedType:
+    case ErrorCode::kUnsupportedMajorPayloadVersion:
+    case ErrorCode::kUnsupportedMinorPayloadVersion:
+    case ErrorCode::kDownloadNewPartitionInfoError:
+    case ErrorCode::kDownloadSignatureMissingInManifest:
+    case ErrorCode::kDownloadManifestParseError:
+    case ErrorCode::kDownloadOperationHashMissingError:
+      return metrics::AttemptResult::kMetadataMalformed;
+
+    case ErrorCode::kDownloadOperationHashMismatch:
+    case ErrorCode::kDownloadOperationHashVerificationError:
+      return metrics::AttemptResult::kOperationMalformed;
+
+    case ErrorCode::kDownloadOperationExecutionError:
+    case ErrorCode::kInstallDeviceOpenError:
+    case ErrorCode::kKernelDeviceOpenError:
+    case ErrorCode::kDownloadWriteError:
+    case ErrorCode::kFilesystemCopierError:
+    case ErrorCode::kFilesystemVerifierError:
+      return metrics::AttemptResult::kOperationExecutionError;
+
+    case ErrorCode::kDownloadMetadataSignatureMismatch:
+      return metrics::AttemptResult::kMetadataVerificationFailed;
+
+    case ErrorCode::kPayloadSizeMismatchError:
+    case ErrorCode::kPayloadHashMismatchError:
+    case ErrorCode::kDownloadPayloadVerificationError:
+    case ErrorCode::kSignedDeltaPayloadExpectedError:
+    case ErrorCode::kDownloadPayloadPubKeyVerificationError:
+      return metrics::AttemptResult::kPayloadVerificationFailed;
+
+    case ErrorCode::kNewRootfsVerificationError:
+    case ErrorCode::kNewKernelVerificationError:
+      return metrics::AttemptResult::kVerificationFailed;
+
+    case ErrorCode::kPostinstallRunnerError:
+    case ErrorCode::kPostinstallBootedFromFirmwareB:
+    case ErrorCode::kPostinstallFirmwareRONotUpdatable:
+      return metrics::AttemptResult::kPostInstallFailed;
+
+    // We should never get these errors in the update-attempt stage so
+    // return internal error if this happens.
+    case ErrorCode::kError:
+    case ErrorCode::kOmahaRequestXMLParseError:
+    case ErrorCode::kOmahaRequestError:
+    case ErrorCode::kOmahaResponseHandlerError:
+    case ErrorCode::kDownloadStateInitializationError:
+    case ErrorCode::kOmahaRequestEmptyResponseError:
+    case ErrorCode::kDownloadInvalidMetadataSignature:
+    case ErrorCode::kOmahaResponseInvalid:
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    case ErrorCode::kOmahaErrorInHTTPResponse:
+    case ErrorCode::kDownloadMetadataSignatureMissingError:
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+    case ErrorCode::kPostinstallPowerwashError:
+    case ErrorCode::kUpdateCanceledByChannelChange:
+    case ErrorCode::kOmahaRequestXMLHasEntityDecl:
+      return metrics::AttemptResult::kInternalError;
+
+    // Special flags. These can't happen (we mask them out above) but
+    // the compiler doesn't know that. Just break out so we can warn and
+    // return |kInternalError|.
+    case ErrorCode::kUmaReportedMax:
+    case ErrorCode::kOmahaRequestHTTPResponseBase:
+    case ErrorCode::kDevModeFlag:
+    case ErrorCode::kResumedFlag:
+    case ErrorCode::kTestImageFlag:
+    case ErrorCode::kTestOmahaUrlFlag:
+    case ErrorCode::kSpecialFlags:
+      break;
+  }
+
+  LOG(ERROR) << "Unexpected error code " << base_code;
+  return metrics::AttemptResult::kInternalError;
+}
+
+metrics::DownloadErrorCode GetDownloadErrorCode(ErrorCode code) {
+  ErrorCode base_code = static_cast<ErrorCode>(
+      static_cast<int>(code) & ~static_cast<int>(ErrorCode::kSpecialFlags));
+
+  if (base_code >= ErrorCode::kOmahaRequestHTTPResponseBase) {
+    int http_status =
+        static_cast<int>(base_code) -
+        static_cast<int>(ErrorCode::kOmahaRequestHTTPResponseBase);
+    if (http_status >= 200 && http_status <= 599) {
+      return static_cast<metrics::DownloadErrorCode>(
+          static_cast<int>(metrics::DownloadErrorCode::kHttpStatus200) +
+          http_status - 200);
+    } else if (http_status == 0) {
+      // The code is using HTTP Status 0 for "Unable to get http
+      // response code."
+      return metrics::DownloadErrorCode::kDownloadError;
+    }
+    LOG(WARNING) << "Unexpected HTTP status code " << http_status;
+    return metrics::DownloadErrorCode::kHttpStatusOther;
+  }
+
+  switch (base_code) {
+    // Unfortunately, ErrorCode::kDownloadTransferError is returned for a wide
+    // variety of errors (proxy errors, host not reachable, timeouts etc.).
+    //
+    // For now just map that to kDownloading. See http://crbug.com/355745
+    // for how we plan to add more detail in the future.
+    case ErrorCode::kDownloadTransferError:
+      return metrics::DownloadErrorCode::kDownloadError;
+
+    // All of these error codes are not related to downloading so break
+    // out so we can warn and return InputMalformed.
+    case ErrorCode::kSuccess:
+    case ErrorCode::kError:
+    case ErrorCode::kOmahaRequestError:
+    case ErrorCode::kOmahaResponseHandlerError:
+    case ErrorCode::kFilesystemCopierError:
+    case ErrorCode::kPostinstallRunnerError:
+    case ErrorCode::kPayloadMismatchedType:
+    case ErrorCode::kInstallDeviceOpenError:
+    case ErrorCode::kKernelDeviceOpenError:
+    case ErrorCode::kPayloadHashMismatchError:
+    case ErrorCode::kPayloadSizeMismatchError:
+    case ErrorCode::kDownloadPayloadVerificationError:
+    case ErrorCode::kDownloadNewPartitionInfoError:
+    case ErrorCode::kDownloadWriteError:
+    case ErrorCode::kNewRootfsVerificationError:
+    case ErrorCode::kNewKernelVerificationError:
+    case ErrorCode::kSignedDeltaPayloadExpectedError:
+    case ErrorCode::kDownloadPayloadPubKeyVerificationError:
+    case ErrorCode::kPostinstallBootedFromFirmwareB:
+    case ErrorCode::kDownloadStateInitializationError:
+    case ErrorCode::kDownloadInvalidMetadataMagicString:
+    case ErrorCode::kDownloadSignatureMissingInManifest:
+    case ErrorCode::kDownloadManifestParseError:
+    case ErrorCode::kDownloadMetadataSignatureError:
+    case ErrorCode::kDownloadMetadataSignatureVerificationError:
+    case ErrorCode::kDownloadMetadataSignatureMismatch:
+    case ErrorCode::kDownloadOperationHashVerificationError:
+    case ErrorCode::kDownloadOperationExecutionError:
+    case ErrorCode::kDownloadOperationHashMismatch:
+    case ErrorCode::kOmahaRequestEmptyResponseError:
+    case ErrorCode::kOmahaRequestXMLParseError:
+    case ErrorCode::kDownloadInvalidMetadataSize:
+    case ErrorCode::kDownloadInvalidMetadataSignature:
+    case ErrorCode::kOmahaResponseInvalid:
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    case ErrorCode::kOmahaErrorInHTTPResponse:
+    case ErrorCode::kDownloadOperationHashMissingError:
+    case ErrorCode::kDownloadMetadataSignatureMissingError:
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+    case ErrorCode::kPostinstallPowerwashError:
+    case ErrorCode::kUpdateCanceledByChannelChange:
+    case ErrorCode::kPostinstallFirmwareRONotUpdatable:
+    case ErrorCode::kUnsupportedMajorPayloadVersion:
+    case ErrorCode::kUnsupportedMinorPayloadVersion:
+    case ErrorCode::kOmahaRequestXMLHasEntityDecl:
+    case ErrorCode::kFilesystemVerifierError:
+      break;
+
+    // Special flags. These can't happen (we mask them out above) but
+    // the compiler doesn't know that. Just break out so we can warn and
+    // return |kInputMalformed|.
+    case ErrorCode::kUmaReportedMax:
+    case ErrorCode::kOmahaRequestHTTPResponseBase:
+    case ErrorCode::kDevModeFlag:
+    case ErrorCode::kResumedFlag:
+    case ErrorCode::kTestImageFlag:
+    case ErrorCode::kTestOmahaUrlFlag:
+    case ErrorCode::kSpecialFlags:
+      LOG(ERROR) << "Unexpected error code " << base_code;
+      break;
+  }
+
+  return metrics::DownloadErrorCode::kInputMalformed;
+}
+
+metrics::ConnectionType GetConnectionType(NetworkConnectionType type,
+                                          NetworkTethering tethering) {
+  switch (type) {
+    case NetworkConnectionType::kUnknown:
+      return metrics::ConnectionType::kUnknown;
+
+    case NetworkConnectionType::kEthernet:
+      if (tethering == NetworkTethering::kConfirmed)
+        return metrics::ConnectionType::kTetheredEthernet;
+      else
+        return metrics::ConnectionType::kEthernet;
+
+    case NetworkConnectionType::kWifi:
+      if (tethering == NetworkTethering::kConfirmed)
+        return metrics::ConnectionType::kTetheredWifi;
+      else
+        return metrics::ConnectionType::kWifi;
+
+    case NetworkConnectionType::kWimax:
+      return metrics::ConnectionType::kWimax;
+
+    case NetworkConnectionType::kBluetooth:
+      return metrics::ConnectionType::kBluetooth;
+
+    case NetworkConnectionType::kCellular:
+      return metrics::ConnectionType::kCellular;
+  }
+
+  LOG(ERROR) << "Unexpected network connection type: type="
+             << static_cast<int>(type)
+             << ", tethering=" << static_cast<int>(tethering);
+
+  return metrics::ConnectionType::kUnknown;
+}
+
+bool WallclockDurationHelper(SystemState* system_state,
+                             const std::string& state_variable_key,
+                             TimeDelta* out_duration) {
+  bool ret = false;
+
+  Time now = system_state->clock()->GetWallclockTime();
+  int64_t stored_value;
+  if (system_state->prefs()->GetInt64(state_variable_key, &stored_value)) {
+    Time stored_time = Time::FromInternalValue(stored_value);
+    if (stored_time > now) {
+      LOG(ERROR) << "Stored time-stamp used for " << state_variable_key
+                 << " is in the future.";
+    } else {
+      *out_duration = now - stored_time;
+      ret = true;
+    }
+  }
+
+  if (!system_state->prefs()->SetInt64(state_variable_key,
+                                       now.ToInternalValue())) {
+    LOG(ERROR) << "Error storing time-stamp in " << state_variable_key;
+  }
+
+  return ret;
+}
+
+bool MonotonicDurationHelper(SystemState* system_state,
+                             int64_t* storage,
+                             TimeDelta* out_duration) {
+  bool ret = false;
+
+  Time now = system_state->clock()->GetMonotonicTime();
+  if (*storage != 0) {
+    Time stored_time = Time::FromInternalValue(*storage);
+    *out_duration = now - stored_time;
+    ret = true;
+  }
+  *storage = now.ToInternalValue();
+
+  return ret;
+}
+
+}  // namespace metrics_utils
+}  // namespace chromeos_update_engine
diff --git a/metrics_utils.h b/metrics_utils.h
new file mode 100644
index 0000000..7c3b02d
--- /dev/null
+++ b/metrics_utils.h
@@ -0,0 +1,71 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_METRICS_UTILS_H_
+#define UPDATE_ENGINE_METRICS_UTILS_H_
+
+#include "update_engine/connection_manager.h"
+#include "update_engine/metrics.h"
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+namespace metrics_utils {
+
+// Transforms a ErrorCode value into a metrics::DownloadErrorCode.
+// This obviously only works for errors related to downloading so if |code|
+// is e.g. |ErrorCode::kFilesystemCopierError| then
+// |kDownloadErrorCodeInputMalformed| is returned.
+metrics::DownloadErrorCode GetDownloadErrorCode(ErrorCode code);
+
+// Transforms a ErrorCode value into a metrics::AttemptResult.
+//
+// If metrics::AttemptResult::kPayloadDownloadError is returned, you
+// can use utils::GetDownloadError() to get more detail.
+metrics::AttemptResult GetAttemptResult(ErrorCode code);
+
+// Calculates the internet connection type given |type| and |tethering|.
+metrics::ConnectionType GetConnectionType(NetworkConnectionType type,
+                                          NetworkTethering tethering);
+
+// This function returns the duration on the wallclock since the last
+// time it was called for the same |state_variable_key| value.
+//
+// If the function returns |true|, the duration (always non-negative)
+// is returned in |out_duration|. If the function returns |false|
+// something went wrong or there was no previous measurement.
+bool WallclockDurationHelper(SystemState* system_state,
+                             const std::string& state_variable_key,
+                             base::TimeDelta* out_duration);
+
+// This function returns the duration on the monotonic clock since the
+// last time it was called for the same |storage| pointer.
+//
+// You should pass a pointer to a 64-bit integer in |storage| which
+// should be initialized to 0.
+//
+// If the function returns |true|, the duration (always non-negative)
+// is returned in |out_duration|. If the function returns |false|
+// something went wrong or there was no previous measurement.
+bool MonotonicDurationHelper(SystemState* system_state,
+                             int64_t* storage,
+                             base::TimeDelta* out_duration);
+
+}  // namespace metrics_utils
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_METRICS_UTILS_H_
diff --git a/metrics_utils_unittest.cc b/metrics_utils_unittest.cc
new file mode 100644
index 0000000..e702c17
--- /dev/null
+++ b/metrics_utils_unittest.cc
@@ -0,0 +1,210 @@
+//
+// Copyright (C) 2015 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 "update_engine/metrics_utils.h"
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/fake_system_state.h"
+
+namespace chromeos_update_engine {
+namespace metrics_utils {
+
+class MetricsUtilsTest : public ::testing::Test {};
+
+TEST(MetricsUtilsTest, GetConnectionType) {
+  // Check that expected combinations map to the right value.
+  EXPECT_EQ(metrics::ConnectionType::kUnknown,
+            GetConnectionType(NetworkConnectionType::kUnknown,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kEthernet,
+            GetConnectionType(NetworkConnectionType::kEthernet,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kWifi,
+            GetConnectionType(NetworkConnectionType::kWifi,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kWimax,
+            GetConnectionType(NetworkConnectionType::kWimax,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kBluetooth,
+            GetConnectionType(NetworkConnectionType::kBluetooth,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kCellular,
+            GetConnectionType(NetworkConnectionType::kCellular,
+                              NetworkTethering::kUnknown));
+  EXPECT_EQ(metrics::ConnectionType::kTetheredEthernet,
+            GetConnectionType(NetworkConnectionType::kEthernet,
+                              NetworkTethering::kConfirmed));
+  EXPECT_EQ(metrics::ConnectionType::kTetheredWifi,
+            GetConnectionType(NetworkConnectionType::kWifi,
+                              NetworkTethering::kConfirmed));
+
+  // Ensure that we don't report tethered ethernet unless it's confirmed.
+  EXPECT_EQ(metrics::ConnectionType::kEthernet,
+            GetConnectionType(NetworkConnectionType::kEthernet,
+                              NetworkTethering::kNotDetected));
+  EXPECT_EQ(metrics::ConnectionType::kEthernet,
+            GetConnectionType(NetworkConnectionType::kEthernet,
+                              NetworkTethering::kSuspected));
+  EXPECT_EQ(metrics::ConnectionType::kEthernet,
+            GetConnectionType(NetworkConnectionType::kEthernet,
+                              NetworkTethering::kUnknown));
+
+  // Ditto for tethered wifi.
+  EXPECT_EQ(metrics::ConnectionType::kWifi,
+            GetConnectionType(NetworkConnectionType::kWifi,
+                              NetworkTethering::kNotDetected));
+  EXPECT_EQ(metrics::ConnectionType::kWifi,
+            GetConnectionType(NetworkConnectionType::kWifi,
+                              NetworkTethering::kSuspected));
+  EXPECT_EQ(metrics::ConnectionType::kWifi,
+            GetConnectionType(NetworkConnectionType::kWifi,
+                              NetworkTethering::kUnknown));
+}
+
+TEST(MetricsUtilsTest, WallclockDurationHelper) {
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  base::TimeDelta duration;
+  const std::string state_variable_key = "test-prefs";
+  FakePrefs fake_prefs;
+
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+
+  // Initialize wallclock to 1 sec.
+  fake_clock.SetWallclockTime(base::Time::FromInternalValue(1000000));
+
+  // First time called so no previous measurement available.
+  EXPECT_FALSE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                      state_variable_key,
+                                                      &duration));
+
+  // Next time, we should get zero since the clock didn't advance.
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // We can also call it as many times as we want with it being
+  // considered a failure.
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // Advance the clock one second, then we should get 1 sec on the
+  // next call and 0 sec on the subsequent call.
+  fake_clock.SetWallclockTime(base::Time::FromInternalValue(2000000));
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 1);
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // Advance clock two seconds and we should get 2 sec and then 0 sec.
+  fake_clock.SetWallclockTime(base::Time::FromInternalValue(4000000));
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 2);
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // There's a possibility that the wallclock can go backwards (NTP
+  // adjustments, for example) so check that we properly handle this
+  // case.
+  fake_clock.SetWallclockTime(base::Time::FromInternalValue(3000000));
+  EXPECT_FALSE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                      state_variable_key,
+                                                      &duration));
+  fake_clock.SetWallclockTime(base::Time::FromInternalValue(4000000));
+  EXPECT_TRUE(metrics_utils::WallclockDurationHelper(&fake_system_state,
+                                                     state_variable_key,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 1);
+}
+
+TEST(MetricsUtilsTest, MonotonicDurationHelper) {
+  int64_t storage = 0;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  base::TimeDelta duration;
+
+  fake_system_state.set_clock(&fake_clock);
+
+  // Initialize monotonic clock to 1 sec.
+  fake_clock.SetMonotonicTime(base::Time::FromInternalValue(1000000));
+
+  // First time called so no previous measurement available.
+  EXPECT_FALSE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                      &storage,
+                                                      &duration));
+
+  // Next time, we should get zero since the clock didn't advance.
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // We can also call it as many times as we want with it being
+  // considered a failure.
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // Advance the clock one second, then we should get 1 sec on the
+  // next call and 0 sec on the subsequent call.
+  fake_clock.SetMonotonicTime(base::Time::FromInternalValue(2000000));
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 1);
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+
+  // Advance clock two seconds and we should get 2 sec and then 0 sec.
+  fake_clock.SetMonotonicTime(base::Time::FromInternalValue(4000000));
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 2);
+  EXPECT_TRUE(metrics_utils::MonotonicDurationHelper(&fake_system_state,
+                                                     &storage,
+                                                     &duration));
+  EXPECT_EQ(duration.InSeconds(), 0);
+}
+
+}  // namespace metrics_utils
+}  // namespace chromeos_update_engine
diff --git a/mock_action.h b/mock_action.h
new file mode 100644
index 0000000..0ba796d
--- /dev/null
+++ b/mock_action.h
@@ -0,0 +1,45 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_ACTION_H_
+#define UPDATE_ENGINE_MOCK_ACTION_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/common/action.h"
+
+namespace chromeos_update_engine {
+
+class MockAction;
+
+template<>
+class ActionTraits<MockAction> {
+ public:
+  typedef NoneType OutputObjectType;
+  typedef NoneType InputObjectType;
+};
+
+class MockAction : public Action<MockAction> {
+ public:
+  MOCK_METHOD0(PerformAction, void());
+  MOCK_CONST_METHOD0(Type, std::string());
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_ACTION_H_
diff --git a/mock_action_processor.h b/mock_action_processor.h
new file mode 100644
index 0000000..c98ff3c
--- /dev/null
+++ b/mock_action_processor.h
@@ -0,0 +1,34 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_ACTION_PROCESSOR_H_
+#define UPDATE_ENGINE_MOCK_ACTION_PROCESSOR_H_
+
+#include <gmock/gmock.h>
+
+#include "update_engine/common/action.h"
+
+namespace chromeos_update_engine {
+
+class MockActionProcessor : public ActionProcessor {
+ public:
+  MOCK_METHOD0(StartProcessing, void());
+  MOCK_METHOD1(EnqueueAction, void(AbstractAction* action));
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_ACTION_PROCESSOR_H_
diff --git a/mock_connection_manager.h b/mock_connection_manager.h
new file mode 100644
index 0000000..109c529
--- /dev/null
+++ b/mock_connection_manager.h
@@ -0,0 +1,43 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_CONNECTION_MANAGER_H_
+#define UPDATE_ENGINE_MOCK_CONNECTION_MANAGER_H_
+
+#include <gmock/gmock.h>
+
+#include "update_engine/connection_manager_interface.h"
+
+namespace chromeos_update_engine {
+
+// This class mocks the generic interface to the connection manager
+// (e.g FlimFlam, Shill, etc.) to consolidate all connection-related
+// logic in update_engine.
+class MockConnectionManager : public ConnectionManagerInterface {
+ public:
+  MockConnectionManager() = default;
+
+  MOCK_METHOD2(GetConnectionProperties,
+               bool(NetworkConnectionType* out_type,
+                    NetworkTethering* out_tethering));
+
+  MOCK_CONST_METHOD2(IsUpdateAllowedOver, bool(NetworkConnectionType type,
+                                               NetworkTethering tethering));
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_CONNECTION_MANAGER_H_
diff --git a/mock_file_writer.h b/mock_file_writer.h
new file mode 100644
index 0000000..72d6a86
--- /dev/null
+++ b/mock_file_writer.h
@@ -0,0 +1,33 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_FILE_WRITER_H_
+#define UPDATE_ENGINE_MOCK_FILE_WRITER_H_
+
+#include <gmock/gmock.h>
+#include "update_engine/payload_consumer/file_writer.h"
+
+namespace chromeos_update_engine {
+
+class MockFileWriter : public FileWriter {
+ public:
+  MOCK_METHOD2(Write, ssize_t(const void* bytes, size_t count));
+  MOCK_METHOD0(Close, int());
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_FILE_WRITER_H_
diff --git a/mock_omaha_request_params.h b/mock_omaha_request_params.h
new file mode 100644
index 0000000..5d5d47b
--- /dev/null
+++ b/mock_omaha_request_params.h
@@ -0,0 +1,91 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_OMAHA_REQUEST_PARAMS_H_
+#define UPDATE_ENGINE_MOCK_OMAHA_REQUEST_PARAMS_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/omaha_request_params.h"
+
+namespace chromeos_update_engine {
+
+class MockOmahaRequestParams : public OmahaRequestParams {
+ public:
+  explicit MockOmahaRequestParams(SystemState* system_state)
+      : OmahaRequestParams(system_state) {
+    // Delegate all calls to the parent instance by default. This helps the
+    // migration from tests using the real RequestParams when they should have
+    // use a fake or mock.
+    ON_CALL(*this, to_more_stable_channel())
+        .WillByDefault(testing::Invoke(
+            this, &MockOmahaRequestParams::fake_to_more_stable_channel));
+    ON_CALL(*this, GetAppId())
+        .WillByDefault(testing::Invoke(
+            this, &MockOmahaRequestParams::FakeGetAppId));
+    ON_CALL(*this, SetTargetChannel(testing::_, testing::_, testing::_))
+        .WillByDefault(testing::Invoke(
+            this, &MockOmahaRequestParams::FakeSetTargetChannel));
+    ON_CALL(*this, UpdateDownloadChannel())
+        .WillByDefault(testing::Invoke(
+            this, &MockOmahaRequestParams::FakeUpdateDownloadChannel));
+    ON_CALL(*this, is_powerwash_allowed())
+        .WillByDefault(testing::Invoke(
+            this, &MockOmahaRequestParams::fake_is_powerwash_allowed));
+  }
+
+  MOCK_CONST_METHOD0(to_more_stable_channel, bool(void));
+  MOCK_CONST_METHOD0(GetAppId, std::string(void));
+  MOCK_METHOD3(SetTargetChannel, bool(const std::string& channel,
+                                      bool is_powerwash_allowed,
+                                      std::string* error));
+  MOCK_METHOD0(UpdateDownloadChannel, void(void));
+  MOCK_CONST_METHOD0(is_powerwash_allowed, bool(void));
+  MOCK_CONST_METHOD0(IsUpdateUrlOfficial, bool(void));
+
+ private:
+  // Wrappers to call the parent class and behave like the real object by
+  // default. See "Delegating Calls to a Parent Class" in gmock's documentation.
+  bool fake_to_more_stable_channel() const {
+    return OmahaRequestParams::to_more_stable_channel();
+  }
+
+  std::string FakeGetAppId() const {
+    return OmahaRequestParams::GetAppId();
+  }
+
+  bool FakeSetTargetChannel(const std::string& channel,
+                            bool is_powerwash_allowed,
+                            std::string* error) {
+    return OmahaRequestParams::SetTargetChannel(channel,
+                                                is_powerwash_allowed,
+                                                error);
+  }
+
+  void FakeUpdateDownloadChannel() {
+    return OmahaRequestParams::UpdateDownloadChannel();
+  }
+
+  bool fake_is_powerwash_allowed() const {
+    return OmahaRequestParams::is_powerwash_allowed();
+  }
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_OMAHA_REQUEST_PARAMS_H_
diff --git a/mock_p2p_manager.h b/mock_p2p_manager.h
new file mode 100644
index 0000000..5f4418e
--- /dev/null
+++ b/mock_p2p_manager.h
@@ -0,0 +1,109 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_P2P_MANAGER_H_
+#define UPDATE_ENGINE_MOCK_P2P_MANAGER_H_
+
+#include <string>
+
+#include "update_engine/fake_p2p_manager.h"
+
+#include <gmock/gmock.h>
+
+namespace chromeos_update_engine {
+
+// A mocked, fake implementation of P2PManager.
+class MockP2PManager : public P2PManager {
+ public:
+  MockP2PManager() {
+    // Delegate all calls to the fake instance
+    ON_CALL(*this, SetDevicePolicy(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::SetDevicePolicy));
+    ON_CALL(*this, IsP2PEnabled())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::IsP2PEnabled));
+    ON_CALL(*this, EnsureP2PRunning())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::EnsureP2PRunning));
+    ON_CALL(*this, EnsureP2PNotRunning())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::EnsureP2PNotRunning));
+    ON_CALL(*this, PerformHousekeeping())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::PerformHousekeeping));
+    ON_CALL(*this, LookupUrlForFile(testing::_, testing::_, testing::_,
+                                    testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::LookupUrlForFile));
+    ON_CALL(*this, FileShare(testing::_, testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileShare));
+    ON_CALL(*this, FileGetPath(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileGetPath));
+    ON_CALL(*this, FileGetSize(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileGetSize));
+    ON_CALL(*this, FileGetExpectedSize(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileGetExpectedSize));
+    ON_CALL(*this, FileGetVisible(testing::_, testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileGetVisible));
+    ON_CALL(*this, FileMakeVisible(testing::_))
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::FileMakeVisible));
+    ON_CALL(*this, CountSharedFiles())
+      .WillByDefault(testing::Invoke(&fake_,
+            &FakeP2PManager::CountSharedFiles));
+  }
+
+  ~MockP2PManager() override {}
+
+  // P2PManager overrides.
+  MOCK_METHOD1(SetDevicePolicy, void(const policy::DevicePolicy*));
+  MOCK_METHOD0(IsP2PEnabled, bool());
+  MOCK_METHOD0(EnsureP2PRunning, bool());
+  MOCK_METHOD0(EnsureP2PNotRunning, bool());
+  MOCK_METHOD0(PerformHousekeeping, bool());
+  MOCK_METHOD4(LookupUrlForFile, void(const std::string&,
+                                      size_t,
+                                      base::TimeDelta,
+                                      LookupCallback));
+  MOCK_METHOD2(FileShare, bool(const std::string&, size_t));
+  MOCK_METHOD1(FileGetPath, base::FilePath(const std::string&));
+  MOCK_METHOD1(FileGetSize, ssize_t(const std::string&));
+  MOCK_METHOD1(FileGetExpectedSize, ssize_t(const std::string&));
+  MOCK_METHOD2(FileGetVisible, bool(const std::string&, bool*));
+  MOCK_METHOD1(FileMakeVisible, bool(const std::string&));
+  MOCK_METHOD0(CountSharedFiles, int());
+
+  // Returns a reference to the underlying FakeP2PManager.
+  FakeP2PManager& fake() {
+    return fake_;
+  }
+
+ private:
+  // The underlying FakeP2PManager.
+  FakeP2PManager fake_;
+
+  DISALLOW_COPY_AND_ASSIGN(MockP2PManager);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_P2P_MANAGER_H_
diff --git a/mock_payload_state.h b/mock_payload_state.h
new file mode 100644
index 0000000..728f274
--- /dev/null
+++ b/mock_payload_state.h
@@ -0,0 +1,81 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_PAYLOAD_STATE_H_
+#define UPDATE_ENGINE_MOCK_PAYLOAD_STATE_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/omaha_request_action.h"
+#include "update_engine/payload_state_interface.h"
+
+namespace chromeos_update_engine {
+
+class MockPayloadState: public PayloadStateInterface {
+ public:
+  bool Initialize(SystemState* system_state) {
+    return true;
+  }
+
+  // Significant methods.
+  MOCK_METHOD1(SetResponse, void(const OmahaResponse& response));
+  MOCK_METHOD0(DownloadComplete, void());
+  MOCK_METHOD1(DownloadProgress, void(size_t count));
+  MOCK_METHOD0(UpdateResumed, void());
+  MOCK_METHOD0(UpdateRestarted, void());
+  MOCK_METHOD0(UpdateSucceeded, void());
+  MOCK_METHOD1(UpdateFailed, void(ErrorCode error));
+  MOCK_METHOD0(ResetUpdateStatus, void());
+  MOCK_METHOD0(ShouldBackoffDownload, bool());
+  MOCK_METHOD0(UpdateEngineStarted, void());
+  MOCK_METHOD0(Rollback, void());
+  MOCK_METHOD1(ExpectRebootInNewVersion,
+               void(const std::string& target_version_uid));
+  MOCK_METHOD0(P2PNewAttempt, void());
+  MOCK_METHOD0(P2PAttemptAllowed, bool());
+  MOCK_METHOD1(SetUsingP2PForDownloading, void(bool value));
+  MOCK_METHOD1(SetUsingP2PForSharing, void(bool value));
+  MOCK_METHOD1(SetScatteringWaitPeriod, void(base::TimeDelta));
+  MOCK_METHOD1(SetP2PUrl, void(const std::string&));
+
+  // Getters.
+  MOCK_METHOD0(GetResponseSignature, std::string());
+  MOCK_METHOD0(GetPayloadAttemptNumber, int());
+  MOCK_METHOD0(GetFullPayloadAttemptNumber, int());
+  MOCK_METHOD0(GetCurrentUrl, std::string());
+  MOCK_METHOD0(GetUrlFailureCount, uint32_t());
+  MOCK_METHOD0(GetUrlSwitchCount, uint32_t());
+  MOCK_METHOD0(GetNumResponsesSeen, int());
+  MOCK_METHOD0(GetBackoffExpiryTime, base::Time());
+  MOCK_METHOD0(GetUpdateDuration, base::TimeDelta());
+  MOCK_METHOD0(GetUpdateDurationUptime, base::TimeDelta());
+  MOCK_METHOD1(GetCurrentBytesDownloaded, uint64_t(DownloadSource source));
+  MOCK_METHOD1(GetTotalBytesDownloaded, uint64_t(DownloadSource source));
+  MOCK_METHOD0(GetNumReboots, uint32_t());
+  MOCK_METHOD0(GetRollbackVersion, std::string());
+  MOCK_METHOD0(GetP2PNumAttempts, int());
+  MOCK_METHOD0(GetP2PFirstAttemptTimestamp, base::Time());
+  MOCK_CONST_METHOD0(GetUsingP2PForDownloading, bool());
+  MOCK_CONST_METHOD0(GetUsingP2PForSharing, bool());
+  MOCK_METHOD0(GetScatteringWaitPeriod, base::TimeDelta());
+  MOCK_CONST_METHOD0(GetP2PUrl, std::string());
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_PAYLOAD_STATE_H_
diff --git a/mock_update_attempter.h b/mock_update_attempter.h
new file mode 100644
index 0000000..89f163e
--- /dev/null
+++ b/mock_update_attempter.h
@@ -0,0 +1,64 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_MOCK_UPDATE_ATTEMPTER_H_
+#define UPDATE_ENGINE_MOCK_UPDATE_ATTEMPTER_H_
+
+#include <string>
+
+#include "update_engine/update_attempter.h"
+
+#include <gmock/gmock.h>
+
+namespace chromeos_update_engine {
+
+class MockUpdateAttempter : public UpdateAttempter {
+ public:
+  using UpdateAttempter::UpdateAttempter;
+
+  MOCK_METHOD6(Update, void(const std::string& app_version,
+                            const std::string& omaha_url,
+                            const std::string& target_channel,
+                            const std::string& target_version_prefix,
+                            bool obey_proxies,
+                            bool interactive));
+
+  MOCK_METHOD5(GetStatus, bool(int64_t* last_checked_time,
+                               double* progress,
+                               std::string* current_operation,
+                               std::string* new_version,
+                               int64_t* new_size));
+
+  MOCK_METHOD1(GetBootTimeAtUpdate, bool(base::Time* out_boot_time));
+
+  MOCK_METHOD0(ResetStatus, bool(void));
+
+  MOCK_METHOD3(CheckForUpdate, void(const std::string& app_version,
+                                    const std::string& omaha_url,
+                                    bool is_interactive));
+
+  MOCK_METHOD0(RefreshDevicePolicy, void(void));
+
+  MOCK_CONST_METHOD0(consecutive_failed_update_checks, unsigned int(void));
+
+  MOCK_CONST_METHOD0(server_dictated_poll_interval, unsigned int(void));
+
+  MOCK_METHOD0(IsAnyUpdateSourceAllowed, bool(void));
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_MOCK_UPDATE_ATTEMPTER_H_
diff --git a/omaha_request_action.cc b/omaha_request_action.cc
new file mode 100644
index 0000000..f2cd032
--- /dev/null
+++ b/omaha_request_action.cc
@@ -0,0 +1,1484 @@
+//
+// Copyright (C) 2012 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 "update_engine/omaha_request_action.h"
+
+#include <inttypes.h>
+
+#include <map>
+#include <sstream>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/logging.h>
+#include <base/rand_util.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+#include <expat.h>
+#include <metrics/metrics_library.h>
+
+#include "update_engine/common/action_pipe.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/connection_manager.h"
+#include "update_engine/metrics.h"
+#include "update_engine/metrics_utils.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/p2p_manager.h"
+#include "update_engine/payload_state_interface.h"
+
+using base::Time;
+using base::TimeDelta;
+using std::map;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+// List of custom pair tags that we interpret in the Omaha Response:
+static const char* kTagDeadline = "deadline";
+static const char* kTagDisablePayloadBackoff = "DisablePayloadBackoff";
+static const char* kTagVersion = "version";
+// Deprecated: "IsDelta"
+static const char* kTagIsDeltaPayload = "IsDeltaPayload";
+static const char* kTagMaxFailureCountPerUrl = "MaxFailureCountPerUrl";
+static const char* kTagMaxDaysToScatter = "MaxDaysToScatter";
+// Deprecated: "ManifestSignatureRsa"
+// Deprecated: "ManifestSize"
+static const char* kTagMetadataSignatureRsa = "MetadataSignatureRsa";
+static const char* kTagMetadataSize = "MetadataSize";
+static const char* kTagMoreInfo = "MoreInfo";
+// Deprecated: "NeedsAdmin"
+static const char* kTagPrompt = "Prompt";
+static const char* kTagSha256 = "sha256";
+static const char* kTagDisableP2PForDownloading = "DisableP2PForDownloading";
+static const char* kTagDisableP2PForSharing = "DisableP2PForSharing";
+static const char* kTagPublicKeyRsa = "PublicKeyRsa";
+
+static const char* kOmahaUpdaterVersion = "0.1.0.0";
+
+namespace {
+
+// Returns an XML ping element attribute assignment with attribute
+// |name| and value |ping_days| if |ping_days| has a value that needs
+// to be sent, or an empty string otherwise.
+string GetPingAttribute(const string& name, int ping_days) {
+  if (ping_days > 0 || ping_days == OmahaRequestAction::kNeverPinged)
+    return base::StringPrintf(" %s=\"%d\"", name.c_str(), ping_days);
+  return "";
+}
+
+// Returns an XML ping element if any of the elapsed days need to be
+// sent, or an empty string otherwise.
+string GetPingXml(int ping_active_days, int ping_roll_call_days) {
+  string ping_active = GetPingAttribute("a", ping_active_days);
+  string ping_roll_call = GetPingAttribute("r", ping_roll_call_days);
+  if (!ping_active.empty() || !ping_roll_call.empty()) {
+    return base::StringPrintf("        <ping active=\"1\"%s%s></ping>\n",
+                              ping_active.c_str(),
+                              ping_roll_call.c_str());
+  }
+  return "";
+}
+
+// Returns an XML that goes into the body of the <app> element of the Omaha
+// request based on the given parameters.
+string GetAppBody(const OmahaEvent* event,
+                  OmahaRequestParams* params,
+                  bool ping_only,
+                  bool include_ping,
+                  int ping_active_days,
+                  int ping_roll_call_days,
+                  PrefsInterface* prefs) {
+  string app_body;
+  if (event == nullptr) {
+    if (include_ping)
+        app_body = GetPingXml(ping_active_days, ping_roll_call_days);
+    if (!ping_only) {
+      app_body += base::StringPrintf(
+          "        <updatecheck targetversionprefix=\"%s\""
+          "></updatecheck>\n",
+          XmlEncodeWithDefault(params->target_version_prefix(), "").c_str());
+
+      // If this is the first update check after a reboot following a previous
+      // update, generate an event containing the previous version number. If
+      // the previous version preference file doesn't exist the event is still
+      // generated with a previous version of 0.0.0.0 -- this is relevant for
+      // older clients or new installs. The previous version event is not sent
+      // for ping-only requests because they come before the client has
+      // rebooted. The previous version event is also not sent if it was already
+      // sent for this new version with a previous updatecheck.
+      string prev_version;
+      if (!prefs->GetString(kPrefsPreviousVersion, &prev_version)) {
+        prev_version = "0.0.0.0";
+      }
+      // We only store a non-empty previous version value after a successful
+      // update in the previous boot. After reporting it back to the server,
+      // we clear the previous version value so it doesn't get reported again.
+      if (!prev_version.empty()) {
+        app_body += base::StringPrintf(
+            "        <event eventtype=\"%d\" eventresult=\"%d\" "
+            "previousversion=\"%s\"></event>\n",
+            OmahaEvent::kTypeRebootedAfterUpdate,
+            OmahaEvent::kResultSuccess,
+            XmlEncodeWithDefault(prev_version, "0.0.0.0").c_str());
+        LOG_IF(WARNING, !prefs->SetString(kPrefsPreviousVersion, ""))
+            << "Unable to reset the previous version.";
+      }
+    }
+  } else {
+    // The error code is an optional attribute so append it only if the result
+    // is not success.
+    string error_code;
+    if (event->result != OmahaEvent::kResultSuccess) {
+      error_code = base::StringPrintf(" errorcode=\"%d\"",
+                                      static_cast<int>(event->error_code));
+    }
+    app_body = base::StringPrintf(
+        "        <event eventtype=\"%d\" eventresult=\"%d\"%s></event>\n",
+        event->type, event->result, error_code.c_str());
+  }
+
+  return app_body;
+}
+
+// Returns the cohort* argument to include in the <app> tag for the passed
+// |arg_name| and |prefs_key|, if any. The return value is suitable to
+// concatenate to the list of arguments and includes a space at the end.
+string GetCohortArgXml(PrefsInterface* prefs,
+                       const string arg_name,
+                       const string prefs_key) {
+  // There's nothing wrong with not having a given cohort setting, so we check
+  // existance first to avoid the warning log message.
+  if (!prefs->Exists(prefs_key))
+    return "";
+  string cohort_value;
+  if (!prefs->GetString(prefs_key, &cohort_value) || cohort_value.empty())
+    return "";
+  // This is a sanity check to avoid sending a huge XML file back to Ohama due
+  // to a compromised stateful partition making the update check fail in low
+  // network environments envent after a reboot.
+  if (cohort_value.size() > 1024) {
+    LOG(WARNING) << "The omaha cohort setting " << arg_name
+                 << " has a too big value, which must be an error or an "
+                    "attacker trying to inhibit updates.";
+    return "";
+  }
+
+  string escaped_xml_value;
+  if (!XmlEncode(cohort_value, &escaped_xml_value)) {
+    LOG(WARNING) << "The omaha cohort setting " << arg_name
+                 << " is ASCII-7 invalid, ignoring it.";
+    return "";
+  }
+
+  return base::StringPrintf("%s=\"%s\" ",
+                            arg_name.c_str(), escaped_xml_value.c_str());
+}
+
+// Returns an XML that corresponds to the entire <app> node of the Omaha
+// request based on the given parameters.
+string GetAppXml(const OmahaEvent* event,
+                 OmahaRequestParams* params,
+                 bool ping_only,
+                 bool include_ping,
+                 int ping_active_days,
+                 int ping_roll_call_days,
+                 int install_date_in_days,
+                 SystemState* system_state) {
+  string app_body = GetAppBody(event, params, ping_only, include_ping,
+                               ping_active_days, ping_roll_call_days,
+                               system_state->prefs());
+  string app_versions;
+
+  // If we are upgrading to a more stable channel and we are allowed to do
+  // powerwash, then pass 0.0.0.0 as the version. This is needed to get the
+  // highest-versioned payload on the destination channel.
+  if (params->to_more_stable_channel() && params->is_powerwash_allowed()) {
+    LOG(INFO) << "Passing OS version as 0.0.0.0 as we are set to powerwash "
+              << "on downgrading to the version in the more stable channel";
+    app_versions = "version=\"0.0.0.0\" from_version=\"" +
+        XmlEncodeWithDefault(params->app_version(), "0.0.0.0") + "\" ";
+  } else {
+    app_versions = "version=\"" +
+        XmlEncodeWithDefault(params->app_version(), "0.0.0.0") + "\" ";
+  }
+
+  string download_channel = params->download_channel();
+  string app_channels =
+      "track=\"" + XmlEncodeWithDefault(download_channel, "") + "\" ";
+  if (params->current_channel() != download_channel) {
+    app_channels += "from_track=\"" + XmlEncodeWithDefault(
+        params->current_channel(), "") + "\" ";
+  }
+
+  string delta_okay_str = params->delta_okay() ? "true" : "false";
+
+  // If install_date_days is not set (e.g. its value is -1 ), don't
+  // include the attribute.
+  string install_date_in_days_str = "";
+  if (install_date_in_days >= 0) {
+    install_date_in_days_str = base::StringPrintf("installdate=\"%d\" ",
+                                                  install_date_in_days);
+  }
+
+  string app_cohort_args;
+  app_cohort_args += GetCohortArgXml(system_state->prefs(),
+                                     "cohort", kPrefsOmahaCohort);
+  app_cohort_args += GetCohortArgXml(system_state->prefs(),
+                                     "cohorthint", kPrefsOmahaCohortHint);
+  app_cohort_args += GetCohortArgXml(system_state->prefs(),
+                                     "cohortname", kPrefsOmahaCohortName);
+
+  string app_xml = "    <app "
+      "appid=\"" + XmlEncodeWithDefault(params->GetAppId(), "") + "\" " +
+      app_cohort_args +
+      app_versions +
+      app_channels +
+      "lang=\"" + XmlEncodeWithDefault(params->app_lang(), "en-US") + "\" " +
+      "board=\"" + XmlEncodeWithDefault(params->os_board(), "") + "\" " +
+      "hardware_class=\"" + XmlEncodeWithDefault(params->hwid(), "") + "\" " +
+      "delta_okay=\"" + delta_okay_str + "\" "
+      "fw_version=\"" + XmlEncodeWithDefault(params->fw_version(), "") + "\" " +
+      "ec_version=\"" + XmlEncodeWithDefault(params->ec_version(), "") + "\" " +
+      install_date_in_days_str +
+      ">\n" +
+         app_body +
+      "    </app>\n";
+
+  return app_xml;
+}
+
+// Returns an XML that corresponds to the entire <os> node of the Omaha
+// request based on the given parameters.
+string GetOsXml(OmahaRequestParams* params) {
+  string os_xml ="    <os "
+      "version=\"" + XmlEncodeWithDefault(params->os_version(), "") + "\" " +
+      "platform=\"" + XmlEncodeWithDefault(params->os_platform(), "") + "\" " +
+      "sp=\"" + XmlEncodeWithDefault(params->os_sp(), "") + "\">"
+      "</os>\n";
+  return os_xml;
+}
+
+// Returns an XML that corresponds to the entire Omaha request based on the
+// given parameters.
+string GetRequestXml(const OmahaEvent* event,
+                     OmahaRequestParams* params,
+                     bool ping_only,
+                     bool include_ping,
+                     int ping_active_days,
+                     int ping_roll_call_days,
+                     int install_date_in_days,
+                     SystemState* system_state) {
+  string os_xml = GetOsXml(params);
+  string app_xml = GetAppXml(event, params, ping_only, include_ping,
+                             ping_active_days, ping_roll_call_days,
+                             install_date_in_days, system_state);
+
+  string install_source = base::StringPrintf("installsource=\"%s\" ",
+      (params->interactive() ? "ondemandupdate" : "scheduler"));
+
+  string updater_version = XmlEncodeWithDefault(
+      base::StringPrintf("%s-%s",
+                         constants::kOmahaUpdaterID,
+                         kOmahaUpdaterVersion), "");
+  string request_xml =
+      "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n"
+      "<request protocol=\"3.0\" " + (
+          "version=\"" + updater_version + "\" "
+          "updaterversion=\"" + updater_version + "\" " +
+          install_source +
+          "ismachine=\"1\">\n") +
+      os_xml +
+      app_xml +
+      "</request>\n";
+
+  return request_xml;
+}
+
+}  // namespace
+
+// Struct used for holding data obtained when parsing the XML.
+struct OmahaParserData {
+  explicit OmahaParserData(XML_Parser _xml_parser) : xml_parser(_xml_parser) {}
+
+  // Pointer to the expat XML_Parser object.
+  XML_Parser xml_parser;
+
+  // This is the state of the parser as it's processing the XML.
+  bool failed = false;
+  bool entity_decl = false;
+  string current_path;
+
+  // These are the values extracted from the XML.
+  string app_cohort;
+  string app_cohorthint;
+  string app_cohortname;
+  bool app_cohort_set = false;
+  bool app_cohorthint_set = false;
+  bool app_cohortname_set = false;
+  string updatecheck_status;
+  string updatecheck_poll_interval;
+  string daystart_elapsed_days;
+  string daystart_elapsed_seconds;
+  vector<string> url_codebase;
+  string package_name;
+  string package_size;
+  string manifest_version;
+  map<string, string> action_postinstall_attrs;
+};
+
+namespace {
+
+// Callback function invoked by expat.
+void ParserHandlerStart(void* user_data, const XML_Char* element,
+                        const XML_Char** attr) {
+  OmahaParserData* data = reinterpret_cast<OmahaParserData*>(user_data);
+
+  if (data->failed)
+    return;
+
+  data->current_path += string("/") + element;
+
+  map<string, string> attrs;
+  if (attr != nullptr) {
+    for (int n = 0; attr[n] != nullptr && attr[n+1] != nullptr; n += 2) {
+      string key = attr[n];
+      string value = attr[n + 1];
+      attrs[key] = value;
+    }
+  }
+
+  if (data->current_path == "/response/app") {
+    if (attrs.find("cohort") != attrs.end()) {
+      data->app_cohort_set = true;
+      data->app_cohort = attrs["cohort"];
+    }
+    if (attrs.find("cohorthint") != attrs.end()) {
+      data->app_cohorthint_set = true;
+      data->app_cohorthint = attrs["cohorthint"];
+    }
+    if (attrs.find("cohortname") != attrs.end()) {
+      data->app_cohortname_set = true;
+      data->app_cohortname = attrs["cohortname"];
+    }
+  } else if (data->current_path == "/response/app/updatecheck") {
+    // There is only supposed to be a single <updatecheck> element.
+    data->updatecheck_status = attrs["status"];
+    data->updatecheck_poll_interval = attrs["PollInterval"];
+  } else if (data->current_path == "/response/daystart") {
+    // Get the install-date.
+    data->daystart_elapsed_days = attrs["elapsed_days"];
+    data->daystart_elapsed_seconds = attrs["elapsed_seconds"];
+  } else if (data->current_path == "/response/app/updatecheck/urls/url") {
+    // Look at all <url> elements.
+    data->url_codebase.push_back(attrs["codebase"]);
+  } else if (data->package_name.empty() && data->current_path ==
+             "/response/app/updatecheck/manifest/packages/package") {
+    // Only look at the first <package>.
+    data->package_name = attrs["name"];
+    data->package_size = attrs["size"];
+  } else if (data->current_path == "/response/app/updatecheck/manifest") {
+    // Get the version.
+    data->manifest_version = attrs[kTagVersion];
+  } else if (data->current_path ==
+             "/response/app/updatecheck/manifest/actions/action") {
+    // We only care about the postinstall action.
+    if (attrs["event"] == "postinstall") {
+      data->action_postinstall_attrs = attrs;
+    }
+  }
+}
+
+// Callback function invoked by expat.
+void ParserHandlerEnd(void* user_data, const XML_Char* element) {
+  OmahaParserData* data = reinterpret_cast<OmahaParserData*>(user_data);
+  if (data->failed)
+    return;
+
+  const string path_suffix = string("/") + element;
+
+  if (!base::EndsWith(data->current_path, path_suffix, true)) {
+    LOG(ERROR) << "Unexpected end element '" << element
+               << "' with current_path='" << data->current_path << "'";
+    data->failed = true;
+    return;
+  }
+  data->current_path.resize(data->current_path.size() - path_suffix.size());
+}
+
+// Callback function invoked by expat.
+//
+// This is called for entity declarations. Since Omaha is guaranteed
+// to never return any XML with entities our course of action is to
+// just stop parsing. This avoids potential resource exhaustion
+// problems AKA the "billion laughs". CVE-2013-0340.
+void ParserHandlerEntityDecl(void *user_data,
+                             const XML_Char *entity_name,
+                             int is_parameter_entity,
+                             const XML_Char *value,
+                             int value_length,
+                             const XML_Char *base,
+                             const XML_Char *system_id,
+                             const XML_Char *public_id,
+                             const XML_Char *notation_name) {
+  OmahaParserData* data = reinterpret_cast<OmahaParserData*>(user_data);
+
+  LOG(ERROR) << "XML entities are not supported. Aborting parsing.";
+  data->failed = true;
+  data->entity_decl = true;
+  XML_StopParser(data->xml_parser, false);
+}
+
+}  // namespace
+
+bool XmlEncode(const string& input, string* output) {
+  if (std::find_if(input.begin(), input.end(),
+                   [](const char c){return c & 0x80;}) != input.end()) {
+    LOG(WARNING) << "Invalid ASCII-7 string passed to the XML encoder:";
+    utils::HexDumpString(input);
+    return false;
+  }
+  output->clear();
+  // We need at least input.size() space in the output, but the code below will
+  // handle it if we need more.
+  output->reserve(input.size());
+  for (char c : input) {
+    switch (c) {
+      case '\"':
+        output->append("&quot;");
+        break;
+      case '\'':
+        output->append("&apos;");
+        break;
+      case '&':
+        output->append("&amp;");
+        break;
+      case '<':
+        output->append("&lt;");
+        break;
+      case '>':
+        output->append("&gt;");
+        break;
+      default:
+        output->push_back(c);
+    }
+  }
+  return true;
+}
+
+string XmlEncodeWithDefault(const string& input, const string& default_value) {
+  string output;
+  if (XmlEncode(input, &output))
+    return output;
+  return default_value;
+}
+
+OmahaRequestAction::OmahaRequestAction(
+    SystemState* system_state,
+    OmahaEvent* event,
+    std::unique_ptr<HttpFetcher> http_fetcher,
+    bool ping_only)
+    : system_state_(system_state),
+      event_(event),
+      http_fetcher_(std::move(http_fetcher)),
+      ping_only_(ping_only),
+      ping_active_days_(0),
+      ping_roll_call_days_(0) {
+  params_ = system_state->request_params();
+}
+
+OmahaRequestAction::~OmahaRequestAction() {}
+
+// Calculates the value to use for the ping days parameter.
+int OmahaRequestAction::CalculatePingDays(const string& key) {
+  int days = kNeverPinged;
+  int64_t last_ping = 0;
+  if (system_state_->prefs()->GetInt64(key, &last_ping) && last_ping >= 0) {
+    days = (Time::Now() - Time::FromInternalValue(last_ping)).InDays();
+    if (days < 0) {
+      // If |days| is negative, then the system clock must have jumped
+      // back in time since the ping was sent. Mark the value so that
+      // it doesn't get sent to the server but we still update the
+      // last ping daystart preference. This way the next ping time
+      // will be correct, hopefully.
+      days = kPingTimeJump;
+      LOG(WARNING) <<
+          "System clock jumped back in time. Resetting ping daystarts.";
+    }
+  }
+  return days;
+}
+
+void OmahaRequestAction::InitPingDays() {
+  // We send pings only along with update checks, not with events.
+  if (IsEvent()) {
+    return;
+  }
+  // TODO(petkov): Figure a way to distinguish active use pings
+  // vs. roll call pings. Currently, the two pings are identical. A
+  // fix needs to change this code as well as UpdateLastPingDays and ShouldPing.
+  ping_active_days_ = CalculatePingDays(kPrefsLastActivePingDay);
+  ping_roll_call_days_ = CalculatePingDays(kPrefsLastRollCallPingDay);
+}
+
+bool OmahaRequestAction::ShouldPing() const {
+  if (ping_active_days_ == OmahaRequestAction::kNeverPinged &&
+      ping_roll_call_days_ == OmahaRequestAction::kNeverPinged) {
+    int powerwash_count = system_state_->hardware()->GetPowerwashCount();
+    if (powerwash_count > 0) {
+      LOG(INFO) << "Not sending ping with a=-1 r=-1 to omaha because "
+                << "powerwash_count is " << powerwash_count;
+      return false;
+    }
+    return true;
+  }
+  return ping_active_days_ > 0 || ping_roll_call_days_ > 0;
+}
+
+// static
+int OmahaRequestAction::GetInstallDate(SystemState* system_state) {
+  PrefsInterface* prefs = system_state->prefs();
+  if (prefs == nullptr)
+    return -1;
+
+  // If we have the value stored on disk, just return it.
+  int64_t stored_value;
+  if (prefs->GetInt64(kPrefsInstallDateDays, &stored_value)) {
+    // Convert and sanity-check.
+    int install_date_days = static_cast<int>(stored_value);
+    if (install_date_days >= 0)
+      return install_date_days;
+    LOG(ERROR) << "Dropping stored Omaha InstallData since its value num_days="
+               << install_date_days << " looks suspicious.";
+    prefs->Delete(kPrefsInstallDateDays);
+  }
+
+  // Otherwise, if OOBE is not complete then do nothing and wait for
+  // ParseResponse() to call ParseInstallDate() and then
+  // PersistInstallDate() to set the kPrefsInstallDateDays state
+  // variable. Once that is done, we'll then report back in future
+  // Omaha requests.  This works exactly because OOBE triggers an
+  // update check.
+  //
+  // However, if OOBE is complete and the kPrefsInstallDateDays state
+  // variable is not set, there are two possibilities
+  //
+  //   1. The update check in OOBE failed so we never got a response
+  //      from Omaha (no network etc.); or
+  //
+  //   2. OOBE was done on an older version that didn't write to the
+  //      kPrefsInstallDateDays state variable.
+  //
+  // In both cases, we approximate the install date by simply
+  // inspecting the timestamp of when OOBE happened.
+
+  Time time_of_oobe;
+  if (!system_state->hardware()->IsOOBEComplete(&time_of_oobe)) {
+    LOG(INFO) << "Not generating Omaha InstallData as we have "
+              << "no prefs file and OOBE is not complete.";
+    return -1;
+  }
+
+  int num_days;
+  if (!utils::ConvertToOmahaInstallDate(time_of_oobe, &num_days)) {
+    LOG(ERROR) << "Not generating Omaha InstallData from time of OOBE "
+               << "as its value '" << utils::ToString(time_of_oobe)
+               << "' looks suspicious.";
+    return -1;
+  }
+
+  // Persist this to disk, for future use.
+  if (!OmahaRequestAction::PersistInstallDate(system_state,
+                                              num_days,
+                                              kProvisionedFromOOBEMarker))
+    return -1;
+
+  LOG(INFO) << "Set the Omaha InstallDate from OOBE time-stamp to "
+            << num_days << " days";
+
+  return num_days;
+}
+
+void OmahaRequestAction::PerformAction() {
+  http_fetcher_->set_delegate(this);
+  InitPingDays();
+  if (ping_only_ && !ShouldPing()) {
+    processor_->ActionComplete(this, ErrorCode::kSuccess);
+    return;
+  }
+
+  string request_post(GetRequestXml(event_.get(),
+                                    params_,
+                                    ping_only_,
+                                    ShouldPing(),  // include_ping
+                                    ping_active_days_,
+                                    ping_roll_call_days_,
+                                    GetInstallDate(system_state_),
+                                    system_state_));
+
+  http_fetcher_->SetPostData(request_post.data(), request_post.size(),
+                             kHttpContentTypeTextXml);
+  LOG(INFO) << "Posting an Omaha request to " << params_->update_url();
+  LOG(INFO) << "Request: " << request_post;
+  http_fetcher_->BeginTransfer(params_->update_url());
+}
+
+void OmahaRequestAction::TerminateProcessing() {
+  http_fetcher_->TerminateTransfer();
+}
+
+// We just store the response in the buffer. Once we've received all bytes,
+// we'll look in the buffer and decide what to do.
+void OmahaRequestAction::ReceivedBytes(HttpFetcher *fetcher,
+                                       const void* bytes,
+                                       size_t length) {
+  const uint8_t* byte_ptr = reinterpret_cast<const uint8_t*>(bytes);
+  response_buffer_.insert(response_buffer_.end(), byte_ptr, byte_ptr + length);
+}
+
+namespace {
+
+// Parses a 64 bit base-10 int from a string and returns it. Returns 0
+// on error. If the string contains "0", that's indistinguishable from
+// error.
+off_t ParseInt(const string& str) {
+  off_t ret = 0;
+  int rc = sscanf(str.c_str(), "%" PRIi64, &ret);  // NOLINT(runtime/printf)
+  if (rc < 1) {
+    // failure
+    return 0;
+  }
+  return ret;
+}
+
+// Parses |str| and returns |true| if, and only if, its value is "true".
+bool ParseBool(const string& str) {
+  return str == "true";
+}
+
+// Update the last ping day preferences based on the server daystart
+// response. Returns true on success, false otherwise.
+bool UpdateLastPingDays(OmahaParserData *parser_data, PrefsInterface* prefs) {
+  int64_t elapsed_seconds = 0;
+  TEST_AND_RETURN_FALSE(
+      base::StringToInt64(parser_data->daystart_elapsed_seconds,
+                          &elapsed_seconds));
+  TEST_AND_RETURN_FALSE(elapsed_seconds >= 0);
+
+  // Remember the local time that matches the server's last midnight
+  // time.
+  Time daystart = Time::Now() - TimeDelta::FromSeconds(elapsed_seconds);
+  prefs->SetInt64(kPrefsLastActivePingDay, daystart.ToInternalValue());
+  prefs->SetInt64(kPrefsLastRollCallPingDay, daystart.ToInternalValue());
+  return true;
+}
+}  // namespace
+
+bool OmahaRequestAction::ParseResponse(OmahaParserData* parser_data,
+                                       OmahaResponse* output_object,
+                                       ScopedActionCompleter* completer) {
+  if (parser_data->updatecheck_status.empty()) {
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  // chromium-os:37289: The PollInterval is not supported by Omaha server
+  // currently.  But still keeping this existing code in case we ever decide to
+  // slow down the request rate from the server-side. Note that the PollInterval
+  // is not persisted, so it has to be sent by the server on every response to
+  // guarantee that the scheduler uses this value (otherwise, if the device got
+  // rebooted after the last server-indicated value, it'll revert to the default
+  // value). Also kDefaultMaxUpdateChecks value for the scattering logic is
+  // based on the assumption that we perform an update check every hour so that
+  // the max value of 8 will roughly be equivalent to one work day. If we decide
+  // to use PollInterval permanently, we should update the
+  // max_update_checks_allowed to take PollInterval into account.  Note: The
+  // parsing for PollInterval happens even before parsing of the status because
+  // we may want to specify the PollInterval even when there's no update.
+  base::StringToInt(parser_data->updatecheck_poll_interval,
+                    &output_object->poll_interval);
+
+  // Check for the "elapsed_days" attribute in the "daystart"
+  // element. This is the number of days since Jan 1 2007, 0:00
+  // PST. If we don't have a persisted value of the Omaha InstallDate,
+  // we'll use it to calculate it and then persist it.
+  if (ParseInstallDate(parser_data, output_object) &&
+      !HasInstallDate(system_state_)) {
+    // Since output_object->install_date_days is never negative, the
+    // elapsed_days -> install-date calculation is reduced to simply
+    // rounding down to the nearest number divisible by 7.
+    int remainder = output_object->install_date_days % 7;
+    int install_date_days_rounded =
+        output_object->install_date_days - remainder;
+    if (PersistInstallDate(system_state_,
+                           install_date_days_rounded,
+                           kProvisionedFromOmahaResponse)) {
+      LOG(INFO) << "Set the Omaha InstallDate from Omaha Response to "
+                << install_date_days_rounded << " days";
+    }
+  }
+
+  // We persist the cohorts sent by omaha even if the status is "noupdate".
+  if (parser_data->app_cohort_set)
+    PersistCohortData(kPrefsOmahaCohort, parser_data->app_cohort);
+  if (parser_data->app_cohorthint_set)
+    PersistCohortData(kPrefsOmahaCohortHint, parser_data->app_cohorthint);
+  if (parser_data->app_cohortname_set)
+    PersistCohortData(kPrefsOmahaCohortName, parser_data->app_cohortname);
+
+  if (!ParseStatus(parser_data, output_object, completer))
+    return false;
+
+  // Note: ParseUrls MUST be called before ParsePackage as ParsePackage
+  // appends the package name to the URLs populated in this method.
+  if (!ParseUrls(parser_data, output_object, completer))
+    return false;
+
+  if (!ParsePackage(parser_data, output_object, completer))
+    return false;
+
+  if (!ParseParams(parser_data, output_object, completer))
+    return false;
+
+  return true;
+}
+
+bool OmahaRequestAction::ParseStatus(OmahaParserData* parser_data,
+                                     OmahaResponse* output_object,
+                                     ScopedActionCompleter* completer) {
+  const string& status = parser_data->updatecheck_status;
+  if (status == "noupdate") {
+    LOG(INFO) << "No update.";
+    output_object->update_exists = false;
+    SetOutputObject(*output_object);
+    completer->set_code(ErrorCode::kSuccess);
+    return false;
+  }
+
+  if (status != "ok") {
+    LOG(ERROR) << "Unknown Omaha response status: " << status;
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  return true;
+}
+
+bool OmahaRequestAction::ParseUrls(OmahaParserData* parser_data,
+                                   OmahaResponse* output_object,
+                                   ScopedActionCompleter* completer) {
+  if (parser_data->url_codebase.empty()) {
+    LOG(ERROR) << "No Omaha Response URLs";
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  LOG(INFO) << "Found " << parser_data->url_codebase.size() << " url(s)";
+  output_object->payload_urls.clear();
+  for (const auto& codebase : parser_data->url_codebase) {
+    if (codebase.empty()) {
+      LOG(ERROR) << "Omaha Response URL has empty codebase";
+      completer->set_code(ErrorCode::kOmahaResponseInvalid);
+      return false;
+    }
+    output_object->payload_urls.push_back(codebase);
+  }
+
+  return true;
+}
+
+bool OmahaRequestAction::ParsePackage(OmahaParserData* parser_data,
+                                      OmahaResponse* output_object,
+                                      ScopedActionCompleter* completer) {
+  if (parser_data->package_name.empty()) {
+    LOG(ERROR) << "Omaha Response has empty package name";
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  // Append the package name to each URL in our list so that we don't
+  // propagate the urlBase vs packageName distinctions beyond this point.
+  // From now on, we only need to use payload_urls.
+  for (auto& payload_url : output_object->payload_urls)
+    payload_url += parser_data->package_name;
+
+  // Parse the payload size.
+  off_t size = ParseInt(parser_data->package_size);
+  if (size <= 0) {
+    LOG(ERROR) << "Omaha Response has invalid payload size: " << size;
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+  output_object->size = size;
+
+  LOG(INFO) << "Payload size = " << output_object->size << " bytes";
+
+  return true;
+}
+
+bool OmahaRequestAction::ParseParams(OmahaParserData* parser_data,
+                                     OmahaResponse* output_object,
+                                     ScopedActionCompleter* completer) {
+  output_object->version = parser_data->manifest_version;
+  if (output_object->version.empty()) {
+    LOG(ERROR) << "Omaha Response does not have version in manifest!";
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  LOG(INFO) << "Received omaha response to update to version "
+            << output_object->version;
+
+  map<string, string> attrs = parser_data->action_postinstall_attrs;
+  if (attrs.empty()) {
+    LOG(ERROR) << "Omaha Response has no postinstall event action";
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  output_object->hash = attrs[kTagSha256];
+  if (output_object->hash.empty()) {
+    LOG(ERROR) << "Omaha Response has empty sha256 value";
+    completer->set_code(ErrorCode::kOmahaResponseInvalid);
+    return false;
+  }
+
+  // Get the optional properties one by one.
+  output_object->more_info_url = attrs[kTagMoreInfo];
+  output_object->metadata_size = ParseInt(attrs[kTagMetadataSize]);
+  output_object->metadata_signature = attrs[kTagMetadataSignatureRsa];
+  output_object->prompt = ParseBool(attrs[kTagPrompt]);
+  output_object->deadline = attrs[kTagDeadline];
+  output_object->max_days_to_scatter = ParseInt(attrs[kTagMaxDaysToScatter]);
+  output_object->disable_p2p_for_downloading =
+      ParseBool(attrs[kTagDisableP2PForDownloading]);
+  output_object->disable_p2p_for_sharing =
+      ParseBool(attrs[kTagDisableP2PForSharing]);
+  output_object->public_key_rsa = attrs[kTagPublicKeyRsa];
+
+  string max = attrs[kTagMaxFailureCountPerUrl];
+  if (!base::StringToUint(max, &output_object->max_failure_count_per_url))
+    output_object->max_failure_count_per_url = kDefaultMaxFailureCountPerUrl;
+
+  output_object->is_delta_payload = ParseBool(attrs[kTagIsDeltaPayload]);
+
+  output_object->disable_payload_backoff =
+      ParseBool(attrs[kTagDisablePayloadBackoff]);
+
+  return true;
+}
+
+// If the transfer was successful, this uses expat to parse the response
+// and fill in the appropriate fields of the output object. Also, notifies
+// the processor that we're done.
+void OmahaRequestAction::TransferComplete(HttpFetcher *fetcher,
+                                          bool successful) {
+  ScopedActionCompleter completer(processor_, this);
+  string current_response(response_buffer_.begin(), response_buffer_.end());
+  LOG(INFO) << "Omaha request response: " << current_response;
+
+  PayloadStateInterface* const payload_state = system_state_->payload_state();
+
+  // Events are best effort transactions -- assume they always succeed.
+  if (IsEvent()) {
+    CHECK(!HasOutputPipe()) << "No output pipe allowed for event requests.";
+    if (event_->result == OmahaEvent::kResultError && successful &&
+        system_state_->hardware()->IsOfficialBuild()) {
+      LOG(INFO) << "Signalling Crash Reporter.";
+      utils::ScheduleCrashReporterUpload();
+    }
+    completer.set_code(ErrorCode::kSuccess);
+    return;
+  }
+
+  if (!successful) {
+    LOG(ERROR) << "Omaha request network transfer failed.";
+    int code = GetHTTPResponseCode();
+    // Makes sure we send sane error values.
+    if (code < 0 || code >= 1000) {
+      code = 999;
+    }
+    completer.set_code(static_cast<ErrorCode>(
+        static_cast<int>(ErrorCode::kOmahaRequestHTTPResponseBase) + code));
+    return;
+  }
+
+  XML_Parser parser = XML_ParserCreate(nullptr);
+  OmahaParserData parser_data(parser);
+  XML_SetUserData(parser, &parser_data);
+  XML_SetElementHandler(parser, ParserHandlerStart, ParserHandlerEnd);
+  XML_SetEntityDeclHandler(parser, ParserHandlerEntityDecl);
+  XML_Status res = XML_Parse(
+      parser,
+      reinterpret_cast<const char*>(response_buffer_.data()),
+      response_buffer_.size(),
+      XML_TRUE);
+  XML_ParserFree(parser);
+
+  if (res != XML_STATUS_OK || parser_data.failed) {
+    LOG(ERROR) << "Omaha response not valid XML: "
+               << XML_ErrorString(XML_GetErrorCode(parser))
+               << " at line " << XML_GetCurrentLineNumber(parser)
+               << " col " << XML_GetCurrentColumnNumber(parser);
+    ErrorCode error_code = ErrorCode::kOmahaRequestXMLParseError;
+    if (response_buffer_.empty()) {
+      error_code = ErrorCode::kOmahaRequestEmptyResponseError;
+    } else if (parser_data.entity_decl) {
+      error_code = ErrorCode::kOmahaRequestXMLHasEntityDecl;
+    }
+    completer.set_code(error_code);
+    return;
+  }
+
+  // Update the last ping day preferences based on the server daystart response
+  // even if we didn't send a ping. Omaha always includes the daystart in the
+  // response, but log the error if it didn't.
+  LOG_IF(ERROR, !UpdateLastPingDays(&parser_data, system_state_->prefs()))
+      << "Failed to update the last ping day preferences!";
+
+  if (!HasOutputPipe()) {
+    // Just set success to whether or not the http transfer succeeded,
+    // which must be true at this point in the code.
+    completer.set_code(ErrorCode::kSuccess);
+    return;
+  }
+
+  OmahaResponse output_object;
+  if (!ParseResponse(&parser_data, &output_object, &completer))
+    return;
+  output_object.update_exists = true;
+  SetOutputObject(output_object);
+
+  if (ShouldIgnoreUpdate(output_object)) {
+    output_object.update_exists = false;
+    completer.set_code(ErrorCode::kOmahaUpdateIgnoredPerPolicy);
+    return;
+  }
+
+  // If Omaha says to disable p2p, respect that
+  if (output_object.disable_p2p_for_downloading) {
+    LOG(INFO) << "Forcibly disabling use of p2p for downloading as "
+              << "requested by Omaha.";
+    payload_state->SetUsingP2PForDownloading(false);
+  }
+  if (output_object.disable_p2p_for_sharing) {
+    LOG(INFO) << "Forcibly disabling use of p2p for sharing as "
+              << "requested by Omaha.";
+    payload_state->SetUsingP2PForSharing(false);
+  }
+
+  // Update the payload state with the current response. The payload state
+  // will automatically reset all stale state if this response is different
+  // from what's stored already. We are updating the payload state as late
+  // as possible in this method so that if a new release gets pushed and then
+  // got pulled back due to some issues, we don't want to clear our internal
+  // state unnecessarily.
+  payload_state->SetResponse(output_object);
+
+  // It could be we've already exceeded the deadline for when p2p is
+  // allowed or that we've tried too many times with p2p. Check that.
+  if (payload_state->GetUsingP2PForDownloading()) {
+    payload_state->P2PNewAttempt();
+    if (!payload_state->P2PAttemptAllowed()) {
+      LOG(INFO) << "Forcibly disabling use of p2p for downloading because "
+                << "of previous failures when using p2p.";
+      payload_state->SetUsingP2PForDownloading(false);
+    }
+  }
+
+  // From here on, we'll complete stuff in CompleteProcessing() so
+  // disable |completer| since we'll create a new one in that
+  // function.
+  completer.set_should_complete(false);
+
+  // If we're allowed to use p2p for downloading we do not pay
+  // attention to wall-clock-based waiting if the URL is indeed
+  // available via p2p. Therefore, check if the file is available via
+  // p2p before deferring...
+  if (payload_state->GetUsingP2PForDownloading()) {
+    LookupPayloadViaP2P(output_object);
+  } else {
+    CompleteProcessing();
+  }
+}
+
+void OmahaRequestAction::CompleteProcessing() {
+  ScopedActionCompleter completer(processor_, this);
+  OmahaResponse& output_object = const_cast<OmahaResponse&>(GetOutputObject());
+  PayloadStateInterface* payload_state = system_state_->payload_state();
+
+  if (ShouldDeferDownload(&output_object)) {
+    output_object.update_exists = false;
+    LOG(INFO) << "Ignoring Omaha updates as updates are deferred by policy.";
+    completer.set_code(ErrorCode::kOmahaUpdateDeferredPerPolicy);
+    return;
+  }
+
+  if (payload_state->ShouldBackoffDownload()) {
+    output_object.update_exists = false;
+    LOG(INFO) << "Ignoring Omaha updates in order to backoff our retry "
+              << "attempts";
+    completer.set_code(ErrorCode::kOmahaUpdateDeferredForBackoff);
+    return;
+  }
+  completer.set_code(ErrorCode::kSuccess);
+}
+
+void OmahaRequestAction::OnLookupPayloadViaP2PCompleted(const string& url) {
+  LOG(INFO) << "Lookup complete, p2p-client returned URL '" << url << "'";
+  if (!url.empty()) {
+    system_state_->payload_state()->SetP2PUrl(url);
+  } else {
+    LOG(INFO) << "Forcibly disabling use of p2p for downloading "
+              << "because no suitable peer could be found.";
+    system_state_->payload_state()->SetUsingP2PForDownloading(false);
+  }
+  CompleteProcessing();
+}
+
+void OmahaRequestAction::LookupPayloadViaP2P(const OmahaResponse& response) {
+  // If the device is in the middle of an update, the state variables
+  // kPrefsUpdateStateNextDataOffset, kPrefsUpdateStateNextDataLength
+  // tracks the offset and length of the operation currently in
+  // progress. The offset is based from the end of the manifest which
+  // is kPrefsManifestMetadataSize bytes long.
+  //
+  // To make forward progress and avoid deadlocks, we need to find a
+  // peer that has at least the entire operation we're currently
+  // working on. Otherwise we may end up in a situation where two
+  // devices bounce back and forth downloading from each other,
+  // neither making any forward progress until one of them decides to
+  // stop using p2p (via kMaxP2PAttempts and kMaxP2PAttemptTimeSeconds
+  // safe-guards). See http://crbug.com/297170 for an example)
+  size_t minimum_size = 0;
+  int64_t manifest_metadata_size = 0;
+  int64_t next_data_offset = 0;
+  int64_t next_data_length = 0;
+  if (system_state_ &&
+      system_state_->prefs()->GetInt64(kPrefsManifestMetadataSize,
+                                       &manifest_metadata_size) &&
+      manifest_metadata_size != -1 &&
+      system_state_->prefs()->GetInt64(kPrefsUpdateStateNextDataOffset,
+                                       &next_data_offset) &&
+      next_data_offset != -1 &&
+      system_state_->prefs()->GetInt64(kPrefsUpdateStateNextDataLength,
+                                       &next_data_length)) {
+    minimum_size = manifest_metadata_size + next_data_offset + next_data_length;
+  }
+
+  string file_id = utils::CalculateP2PFileId(response.hash, response.size);
+  if (system_state_->p2p_manager()) {
+    LOG(INFO) << "Checking if payload is available via p2p, file_id="
+              << file_id << " minimum_size=" << minimum_size;
+    system_state_->p2p_manager()->LookupUrlForFile(
+        file_id,
+        minimum_size,
+        TimeDelta::FromSeconds(kMaxP2PNetworkWaitTimeSeconds),
+        base::Bind(&OmahaRequestAction::OnLookupPayloadViaP2PCompleted,
+                   base::Unretained(this)));
+  }
+}
+
+bool OmahaRequestAction::ShouldDeferDownload(OmahaResponse* output_object) {
+  if (params_->interactive()) {
+    LOG(INFO) << "Not deferring download because update is interactive.";
+    return false;
+  }
+
+  // If we're using p2p to download _and_ we have a p2p URL, we never
+  // defer the download. This is because the download will always
+  // happen from a peer on the LAN and we've been waiting in line for
+  // our turn.
+  const PayloadStateInterface* payload_state = system_state_->payload_state();
+  if (payload_state->GetUsingP2PForDownloading() &&
+      !payload_state->GetP2PUrl().empty()) {
+    LOG(INFO) << "Download not deferred because download "
+              << "will happen from a local peer (via p2p).";
+    return false;
+  }
+
+  // We should defer the downloads only if we've first satisfied the
+  // wall-clock-based-waiting period and then the update-check-based waiting
+  // period, if required.
+  if (!params_->wall_clock_based_wait_enabled()) {
+    LOG(INFO) << "Wall-clock-based waiting period is not enabled,"
+              << " so no deferring needed.";
+    return false;
+  }
+
+  switch (IsWallClockBasedWaitingSatisfied(output_object)) {
+    case kWallClockWaitNotSatisfied:
+      // We haven't even satisfied the first condition, passing the
+      // wall-clock-based waiting period, so we should defer the downloads
+      // until that happens.
+      LOG(INFO) << "wall-clock-based-wait not satisfied.";
+      return true;
+
+    case kWallClockWaitDoneButUpdateCheckWaitRequired:
+      LOG(INFO) << "wall-clock-based-wait satisfied and "
+                << "update-check-based-wait required.";
+      return !IsUpdateCheckCountBasedWaitingSatisfied();
+
+    case kWallClockWaitDoneAndUpdateCheckWaitNotRequired:
+      // Wall-clock-based waiting period is satisfied, and it's determined
+      // that we do not need the update-check-based wait. so no need to
+      // defer downloads.
+      LOG(INFO) << "wall-clock-based-wait satisfied and "
+                << "update-check-based-wait is not required.";
+      return false;
+
+    default:
+      // Returning false for this default case so we err on the
+      // side of downloading updates than deferring in case of any bugs.
+      NOTREACHED();
+      return false;
+  }
+}
+
+OmahaRequestAction::WallClockWaitResult
+OmahaRequestAction::IsWallClockBasedWaitingSatisfied(
+    OmahaResponse* output_object) {
+  Time update_first_seen_at;
+  int64_t update_first_seen_at_int;
+
+  if (system_state_->prefs()->Exists(kPrefsUpdateFirstSeenAt)) {
+    if (system_state_->prefs()->GetInt64(kPrefsUpdateFirstSeenAt,
+                                         &update_first_seen_at_int)) {
+      // Note: This timestamp could be that of ANY update we saw in the past
+      // (not necessarily this particular update we're considering to apply)
+      // but never got to apply because of some reason (e.g. stop AU policy,
+      // updates being pulled out from Omaha, changes in target version prefix,
+      // new update being rolled out, etc.). But for the purposes of scattering
+      // it doesn't matter which update the timestamp corresponds to. i.e.
+      // the clock starts ticking the first time we see an update and we're
+      // ready to apply when the random wait period is satisfied relative to
+      // that first seen timestamp.
+      update_first_seen_at = Time::FromInternalValue(update_first_seen_at_int);
+      LOG(INFO) << "Using persisted value of UpdateFirstSeenAt: "
+                << utils::ToString(update_first_seen_at);
+    } else {
+      // This seems like an unexpected error where the persisted value exists
+      // but it's not readable for some reason. Just skip scattering in this
+      // case to be safe.
+     LOG(INFO) << "Not scattering as UpdateFirstSeenAt value cannot be read";
+     return kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+    }
+  } else {
+    update_first_seen_at = Time::Now();
+    update_first_seen_at_int = update_first_seen_at.ToInternalValue();
+    if (system_state_->prefs()->SetInt64(kPrefsUpdateFirstSeenAt,
+                                         update_first_seen_at_int)) {
+      LOG(INFO) << "Persisted the new value for UpdateFirstSeenAt: "
+                << utils::ToString(update_first_seen_at);
+    } else {
+      // This seems like an unexpected error where the value cannot be
+      // persisted for some reason. Just skip scattering in this
+      // case to be safe.
+      LOG(INFO) << "Not scattering as UpdateFirstSeenAt value "
+                << utils::ToString(update_first_seen_at)
+                << " cannot be persisted";
+     return kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+    }
+  }
+
+  TimeDelta elapsed_time = Time::Now() - update_first_seen_at;
+  TimeDelta max_scatter_period = TimeDelta::FromDays(
+      output_object->max_days_to_scatter);
+
+  LOG(INFO) << "Waiting Period = "
+            << utils::FormatSecs(params_->waiting_period().InSeconds())
+            << ", Time Elapsed = "
+            << utils::FormatSecs(elapsed_time.InSeconds())
+            << ", MaxDaysToScatter = "
+            << max_scatter_period.InDays();
+
+  if (!output_object->deadline.empty()) {
+    // The deadline is set for all rules which serve a delta update from a
+    // previous FSI, which means this update will be applied mostly in OOBE
+    // cases. For these cases, we shouldn't scatter so as to finish the OOBE
+    // quickly.
+    LOG(INFO) << "Not scattering as deadline flag is set";
+    return kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+  }
+
+  if (max_scatter_period.InDays() == 0) {
+    // This means the Omaha rule creator decides that this rule
+    // should not be scattered irrespective of the policy.
+    LOG(INFO) << "Not scattering as MaxDaysToScatter in rule is 0.";
+    return kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+  }
+
+  if (elapsed_time > max_scatter_period) {
+    // This means we've waited more than the upperbound wait in the rule
+    // from the time we first saw a valid update available to us.
+    // This will prevent update starvation.
+    LOG(INFO) << "Not scattering as we're past the MaxDaysToScatter limit.";
+    return kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+  }
+
+  // This means we are required to participate in scattering.
+  // See if our turn has arrived now.
+  TimeDelta remaining_wait_time = params_->waiting_period() - elapsed_time;
+  if (remaining_wait_time.InSeconds() <= 0) {
+    // Yes, it's our turn now.
+    LOG(INFO) << "Successfully passed the wall-clock-based-wait.";
+
+    // But we can't download until the update-check-count-based wait is also
+    // satisfied, so mark it as required now if update checks are enabled.
+    return params_->update_check_count_wait_enabled() ?
+              kWallClockWaitDoneButUpdateCheckWaitRequired :
+              kWallClockWaitDoneAndUpdateCheckWaitNotRequired;
+  }
+
+  // Not our turn yet, so we have to wait until our turn to
+  // help scatter the downloads across all clients of the enterprise.
+  LOG(INFO) << "Update deferred for another "
+            << utils::FormatSecs(remaining_wait_time.InSeconds())
+            << " per policy.";
+  return kWallClockWaitNotSatisfied;
+}
+
+bool OmahaRequestAction::IsUpdateCheckCountBasedWaitingSatisfied() {
+  int64_t update_check_count_value;
+
+  if (system_state_->prefs()->Exists(kPrefsUpdateCheckCount)) {
+    if (!system_state_->prefs()->GetInt64(kPrefsUpdateCheckCount,
+                                          &update_check_count_value)) {
+      // We are unable to read the update check count from file for some reason.
+      // So let's proceed anyway so as to not stall the update.
+      LOG(ERROR) << "Unable to read update check count. "
+                 << "Skipping update-check-count-based-wait.";
+      return true;
+    }
+  } else {
+    // This file does not exist. This means we haven't started our update
+    // check count down yet, so this is the right time to start the count down.
+    update_check_count_value = base::RandInt(
+      params_->min_update_checks_needed(),
+      params_->max_update_checks_allowed());
+
+    LOG(INFO) << "Randomly picked update check count value = "
+              << update_check_count_value;
+
+    // Write out the initial value of update_check_count_value.
+    if (!system_state_->prefs()->SetInt64(kPrefsUpdateCheckCount,
+                                          update_check_count_value)) {
+      // We weren't able to write the update check count file for some reason.
+      // So let's proceed anyway so as to not stall the update.
+      LOG(ERROR) << "Unable to write update check count. "
+                 << "Skipping update-check-count-based-wait.";
+      return true;
+    }
+  }
+
+  if (update_check_count_value == 0) {
+    LOG(INFO) << "Successfully passed the update-check-based-wait.";
+    return true;
+  }
+
+  if (update_check_count_value < 0 ||
+      update_check_count_value > params_->max_update_checks_allowed()) {
+    // We err on the side of skipping scattering logic instead of stalling
+    // a machine from receiving any updates in case of any unexpected state.
+    LOG(ERROR) << "Invalid value for update check count detected. "
+               << "Skipping update-check-count-based-wait.";
+    return true;
+  }
+
+  // Legal value, we need to wait for more update checks to happen
+  // until this becomes 0.
+  LOG(INFO) << "Deferring Omaha updates for another "
+            << update_check_count_value
+            << " update checks per policy";
+  return false;
+}
+
+// static
+bool OmahaRequestAction::ParseInstallDate(OmahaParserData* parser_data,
+                                          OmahaResponse* output_object) {
+  int64_t elapsed_days = 0;
+  if (!base::StringToInt64(parser_data->daystart_elapsed_days,
+                           &elapsed_days))
+    return false;
+
+  if (elapsed_days < 0)
+    return false;
+
+  output_object->install_date_days = elapsed_days;
+  return true;
+}
+
+// static
+bool OmahaRequestAction::HasInstallDate(SystemState *system_state) {
+  PrefsInterface* prefs = system_state->prefs();
+  if (prefs == nullptr)
+    return false;
+
+  return prefs->Exists(kPrefsInstallDateDays);
+}
+
+// static
+bool OmahaRequestAction::PersistInstallDate(
+    SystemState *system_state,
+    int install_date_days,
+    InstallDateProvisioningSource source) {
+  TEST_AND_RETURN_FALSE(install_date_days >= 0);
+
+  PrefsInterface* prefs = system_state->prefs();
+  if (prefs == nullptr)
+    return false;
+
+  if (!prefs->SetInt64(kPrefsInstallDateDays, install_date_days))
+    return false;
+
+  string metric_name = metrics::kMetricInstallDateProvisioningSource;
+  system_state->metrics_lib()->SendEnumToUMA(
+      metric_name,
+      static_cast<int>(source),  // Sample.
+      kProvisionedMax);          // Maximum.
+
+  return true;
+}
+
+bool OmahaRequestAction::PersistCohortData(
+    const string& prefs_key,
+    const string& new_value) {
+  if (new_value.empty() && system_state_->prefs()->Exists(prefs_key)) {
+    LOG(INFO) << "Removing stored " << prefs_key << " value.";
+    return system_state_->prefs()->Delete(prefs_key);
+  } else if (!new_value.empty()) {
+    LOG(INFO) << "Storing new setting " << prefs_key << " as " << new_value;
+    return system_state_->prefs()->SetString(prefs_key, new_value);
+  }
+  return true;
+}
+
+void OmahaRequestAction::ActionCompleted(ErrorCode code) {
+  // We only want to report this on "update check".
+  if (ping_only_ || event_ != nullptr)
+    return;
+
+  metrics::CheckResult result = metrics::CheckResult::kUnset;
+  metrics::CheckReaction reaction = metrics::CheckReaction::kUnset;
+  metrics::DownloadErrorCode download_error_code =
+      metrics::DownloadErrorCode::kUnset;
+
+  // Regular update attempt.
+  switch (code) {
+  case ErrorCode::kSuccess:
+    // OK, we parsed the response successfully but that does
+    // necessarily mean that an update is available.
+    if (HasOutputPipe()) {
+      const OmahaResponse& response = GetOutputObject();
+      if (response.update_exists) {
+        result = metrics::CheckResult::kUpdateAvailable;
+        reaction = metrics::CheckReaction::kUpdating;
+      } else {
+        result = metrics::CheckResult::kNoUpdateAvailable;
+      }
+    } else {
+      result = metrics::CheckResult::kNoUpdateAvailable;
+    }
+    break;
+
+  case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    result = metrics::CheckResult::kUpdateAvailable;
+    reaction = metrics::CheckReaction::kIgnored;
+    break;
+
+  case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    result = metrics::CheckResult::kUpdateAvailable;
+    reaction = metrics::CheckReaction::kDeferring;
+    break;
+
+  case ErrorCode::kOmahaUpdateDeferredForBackoff:
+    result = metrics::CheckResult::kUpdateAvailable;
+    reaction = metrics::CheckReaction::kBackingOff;
+    break;
+
+  default:
+    // We report two flavors of errors, "Download errors" and "Parsing
+    // error". Try to convert to the former and if that doesn't work
+    // we know it's the latter.
+    metrics::DownloadErrorCode tmp_error =
+        metrics_utils::GetDownloadErrorCode(code);
+    if (tmp_error != metrics::DownloadErrorCode::kInputMalformed) {
+      result = metrics::CheckResult::kDownloadError;
+      download_error_code = tmp_error;
+    } else {
+      result = metrics::CheckResult::kParsingError;
+    }
+    break;
+  }
+
+  metrics::ReportUpdateCheckMetrics(system_state_,
+                                    result, reaction, download_error_code);
+}
+
+bool OmahaRequestAction::ShouldIgnoreUpdate(
+    const OmahaResponse& response) const {
+  // Note: policy decision to not update to a version we rolled back from.
+  string rollback_version =
+      system_state_->payload_state()->GetRollbackVersion();
+  if (!rollback_version.empty()) {
+    LOG(INFO) << "Detected previous rollback from version " << rollback_version;
+    if (rollback_version == response.version) {
+      LOG(INFO) << "Received version that we rolled back from. Ignoring.";
+      return true;
+    }
+  }
+
+  if (!IsUpdateAllowedOverCurrentConnection()) {
+    LOG(INFO) << "Update is not allowed over current connection.";
+    return true;
+  }
+
+  // Note: We could technically delete the UpdateFirstSeenAt state when we
+  // return true. If we do, it'll mean a device has to restart the
+  // UpdateFirstSeenAt and thus help scattering take effect when the AU is
+  // turned on again. On the other hand, it also increases the chance of update
+  // starvation if an admin turns AU on/off more frequently. We choose to err on
+  // the side of preventing starvation at the cost of not applying scattering in
+  // those cases.
+  return false;
+}
+
+bool OmahaRequestAction::IsUpdateAllowedOverCurrentConnection() const {
+  NetworkConnectionType type;
+  NetworkTethering tethering;
+  ConnectionManagerInterface* connection_manager =
+      system_state_->connection_manager();
+  if (!connection_manager->GetConnectionProperties(&type, &tethering)) {
+    LOG(INFO) << "We could not determine our connection type. "
+              << "Defaulting to allow updates.";
+    return true;
+  }
+  bool is_allowed = connection_manager->IsUpdateAllowedOver(type, tethering);
+  LOG(INFO) << "We are connected via "
+            << ConnectionManager::StringForConnectionType(type)
+            << ", Updates allowed: " << (is_allowed ? "Yes" : "No");
+  return is_allowed;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/omaha_request_action.h b/omaha_request_action.h
new file mode 100644
index 0000000..1aeaf8a
--- /dev/null
+++ b/omaha_request_action.h
@@ -0,0 +1,332 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_OMAHA_REQUEST_ACTION_H_
+#define UPDATE_ENGINE_OMAHA_REQUEST_ACTION_H_
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include <brillo/secure_blob.h>
+#include <curl/curl.h>
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/http_fetcher.h"
+#include "update_engine/omaha_response.h"
+#include "update_engine/system_state.h"
+
+// The Omaha Request action makes a request to Omaha and can output
+// the response on the output ActionPipe.
+
+namespace chromeos_update_engine {
+
+// Encodes XML entities in a given string. Input must be ASCII-7 valid. If
+// the input is invalid, the default value is used instead.
+std::string XmlEncodeWithDefault(const std::string& input,
+                                 const std::string& default_value);
+
+// Escapes text so it can be included as character data and attribute
+// values. The |input| string must be valid ASCII-7, no UTF-8 supported.
+// Returns whether the |input| was valid and escaped properly in |output|.
+bool XmlEncode(const std::string& input, std::string* output);
+
+// This struct encapsulates the Omaha event information. For a
+// complete list of defined event types and results, see
+// http://code.google.com/p/omaha/wiki/ServerProtocol#event
+struct OmahaEvent {
+  // The Type values correspond to EVENT_TYPE values of Omaha.
+  enum Type {
+    kTypeUnknown = 0,
+    kTypeDownloadComplete = 1,
+    kTypeInstallComplete = 2,
+    kTypeUpdateComplete = 3,
+    kTypeUpdateDownloadStarted = 13,
+    kTypeUpdateDownloadFinished = 14,
+    // Chromium OS reserved type sent after the first reboot following an update
+    // completed.
+    kTypeRebootedAfterUpdate = 54,
+  };
+
+  // The Result values correspond to EVENT_RESULT values of Omaha.
+  enum Result {
+    kResultError = 0,
+    kResultSuccess = 1,
+    kResultUpdateDeferred = 9,  // When we ignore/defer updates due to policy.
+  };
+
+  OmahaEvent()
+      : type(kTypeUnknown),
+        result(kResultError),
+        error_code(ErrorCode::kError) {}
+  explicit OmahaEvent(Type in_type)
+      : type(in_type),
+        result(kResultSuccess),
+        error_code(ErrorCode::kSuccess) {}
+  OmahaEvent(Type in_type, Result in_result, ErrorCode in_error_code)
+      : type(in_type),
+        result(in_result),
+        error_code(in_error_code) {}
+
+  Type type;
+  Result result;
+  ErrorCode error_code;
+};
+
+class NoneType;
+class OmahaRequestAction;
+class OmahaRequestParams;
+class PrefsInterface;
+
+// This struct is declared in the .cc file.
+struct OmahaParserData;
+
+template<>
+class ActionTraits<OmahaRequestAction> {
+ public:
+  // Takes parameters on the input pipe.
+  typedef NoneType InputObjectType;
+  // On UpdateCheck success, puts the Omaha response on output. Event
+  // requests do not have an output pipe.
+  typedef OmahaResponse OutputObjectType;
+};
+
+class OmahaRequestAction : public Action<OmahaRequestAction>,
+                           public HttpFetcherDelegate {
+ public:
+  static const int kNeverPinged = -1;
+  static const int kPingTimeJump = -2;
+  // We choose this value of 10 as a heuristic for a work day in trying
+  // each URL, assuming we check roughly every 45 mins. This is a good time to
+  // wait - neither too long nor too little - so we don't give up the preferred
+  // URLs that appear earlier in list too quickly before moving on to the
+  // fallback ones.
+  static const int kDefaultMaxFailureCountPerUrl = 10;
+
+  // These are the possible outcome upon checking whether we satisfied
+  // the wall-clock-based-wait.
+  enum WallClockWaitResult {
+    kWallClockWaitNotSatisfied,
+    kWallClockWaitDoneButUpdateCheckWaitRequired,
+    kWallClockWaitDoneAndUpdateCheckWaitNotRequired,
+  };
+
+  // The ctor takes in all the parameters that will be used for making
+  // the request to Omaha. For some of them we have constants that
+  // should be used.
+  //
+  // Takes ownership of the passed in HttpFetcher. Useful for testing.
+  //
+  // Takes ownership of the passed in OmahaEvent. If |event| is null,
+  // this is an UpdateCheck request, otherwise it's an Event request.
+  // Event requests always succeed.
+  //
+  // A good calling pattern is:
+  // OmahaRequestAction(..., new OmahaEvent(...), new WhateverHttpFetcher);
+  // or
+  // OmahaRequestAction(..., nullptr, new WhateverHttpFetcher);
+  OmahaRequestAction(SystemState* system_state,
+                     OmahaEvent* event,
+                     std::unique_ptr<HttpFetcher> http_fetcher,
+                     bool ping_only);
+  ~OmahaRequestAction() override;
+  typedef ActionTraits<OmahaRequestAction>::InputObjectType InputObjectType;
+  typedef ActionTraits<OmahaRequestAction>::OutputObjectType OutputObjectType;
+  void PerformAction() override;
+  void TerminateProcessing() override;
+  void ActionCompleted(ErrorCode code) override;
+
+  int GetHTTPResponseCode() { return http_fetcher_->http_response_code(); }
+
+  // Debugging/logging
+  static std::string StaticType() { return "OmahaRequestAction"; }
+  std::string Type() const override { return StaticType(); }
+
+  // Delegate methods (see http_fetcher.h)
+  void ReceivedBytes(HttpFetcher *fetcher,
+                     const void* bytes, size_t length) override;
+
+  void TransferComplete(HttpFetcher *fetcher, bool successful) override;
+
+  // Returns true if this is an Event request, false if it's an UpdateCheck.
+  bool IsEvent() const { return event_.get() != nullptr; }
+
+ private:
+  FRIEND_TEST(OmahaRequestActionTest, GetInstallDateWhenNoPrefsNorOOBE);
+  FRIEND_TEST(OmahaRequestActionTest,
+              GetInstallDateWhenOOBECompletedWithInvalidDate);
+  FRIEND_TEST(OmahaRequestActionTest,
+              GetInstallDateWhenOOBECompletedWithValidDate);
+  FRIEND_TEST(OmahaRequestActionTest,
+              GetInstallDateWhenOOBECompletedDateChanges);
+
+  // Enumeration used in PersistInstallDate().
+  enum InstallDateProvisioningSource {
+    kProvisionedFromOmahaResponse,
+    kProvisionedFromOOBEMarker,
+
+    // kProvisionedMax is the count of the number of enums above. Add
+    // any new enums above this line only.
+    kProvisionedMax
+  };
+
+  // Gets the install date, expressed as the number of PST8PDT
+  // calendar weeks since January 1st 2007, times seven. Returns -1 if
+  // unknown. See http://crbug.com/336838 for details about this value.
+  static int GetInstallDate(SystemState* system_state);
+
+  // Parses the Omaha Response in |doc| and sets the
+  // |install_date_days| field of |output_object| to the value of the
+  // elapsed_days attribute of the daystart element. Returns True if
+  // the value was set, False if it wasn't found.
+  static bool ParseInstallDate(OmahaParserData* parser_data,
+                               OmahaResponse* output_object);
+
+  // Returns True if the kPrefsInstallDateDays state variable is set,
+  // False otherwise.
+  static bool HasInstallDate(SystemState *system_state);
+
+  // Writes |install_date_days| into the kPrefsInstallDateDays state
+  // variable and emits an UMA stat for the |source| used. Returns
+  // True if the value was written, False if an error occurred.
+  static bool PersistInstallDate(SystemState *system_state,
+                                 int install_date_days,
+                                 InstallDateProvisioningSource source);
+
+  // Persist the new cohort* value received in the XML file in the |prefs_key|
+  // preference file. If the |new_value| is empty, the currently stored value
+  // will be deleted. Don't call this function with an empty |new_value| if the
+  // value was not set in the XML, since that would delete the stored value.
+  bool PersistCohortData(const std::string& prefs_key,
+                         const std::string& new_value);
+
+  // If this is an update check request, initializes
+  // |ping_active_days_| and |ping_roll_call_days_| to values that may
+  // be sent as pings to Omaha.
+  void InitPingDays();
+
+  // Based on the persistent preference store values, calculates the
+  // number of days since the last ping sent for |key|.
+  int CalculatePingDays(const std::string& key);
+
+  // Returns whether we have "active_days" or "roll_call_days" ping values to
+  // send to Omaha and thus we should include them in the response.
+  bool ShouldPing() const;
+
+  // Returns true if the download of a new update should be deferred.
+  // False if the update can be downloaded.
+  bool ShouldDeferDownload(OmahaResponse* output_object);
+
+  // Returns true if the basic wall-clock-based waiting period has been
+  // satisfied based on the scattering policy setting. False otherwise.
+  // If true, it also indicates whether the additional update-check-count-based
+  // waiting period also needs to be satisfied before the download can begin.
+  WallClockWaitResult IsWallClockBasedWaitingSatisfied(
+      OmahaResponse* output_object);
+
+  // Returns true if the update-check-count-based waiting period has been
+  // satisfied. False otherwise.
+  bool IsUpdateCheckCountBasedWaitingSatisfied();
+
+  // Parses the response from Omaha that's available in |doc| using the other
+  // helper methods below and populates the |output_object| with the relevant
+  // values. Returns true if we should continue the parsing.  False otherwise,
+  // in which case it sets any error code using |completer|.
+  bool ParseResponse(OmahaParserData* parser_data,
+                     OmahaResponse* output_object,
+                     ScopedActionCompleter* completer);
+
+  // Parses the status property in the given update_check_node and populates
+  // |output_object| if valid. Returns true if we should continue the parsing.
+  // False otherwise, in which case it sets any error code using |completer|.
+  bool ParseStatus(OmahaParserData* parser_data,
+                   OmahaResponse* output_object,
+                   ScopedActionCompleter* completer);
+
+  // Parses the URL nodes in the given XML document and populates
+  // |output_object| if valid. Returns true if we should continue the parsing.
+  // False otherwise, in which case it sets any error code using |completer|.
+  bool ParseUrls(OmahaParserData* parser_data,
+                 OmahaResponse* output_object,
+                 ScopedActionCompleter* completer);
+
+  // Parses the package node in the given XML document and populates
+  // |output_object| if valid. Returns true if we should continue the parsing.
+  // False otherwise, in which case it sets any error code using |completer|.
+  bool ParsePackage(OmahaParserData* parser_data,
+                    OmahaResponse* output_object,
+                    ScopedActionCompleter* completer);
+
+  // Parses the other parameters in the given XML document and populates
+  // |output_object| if valid. Returns true if we should continue the parsing.
+  // False otherwise, in which case it sets any error code using |completer|.
+  bool ParseParams(OmahaParserData* parser_data,
+                   OmahaResponse* output_object,
+                   ScopedActionCompleter* completer);
+
+  // Called by TransferComplete() to complete processing, either
+  // asynchronously after looking up resources via p2p or directly.
+  void CompleteProcessing();
+
+  // Helper to asynchronously look up payload on the LAN.
+  void LookupPayloadViaP2P(const OmahaResponse& response);
+
+  // Callback used by LookupPayloadViaP2P().
+  void OnLookupPayloadViaP2PCompleted(const std::string& url);
+
+  // Returns true if the current update should be ignored.
+  bool ShouldIgnoreUpdate(const OmahaResponse& response) const;
+
+  // Returns true if updates are allowed over the current type of connection.
+  // False otherwise.
+  bool IsUpdateAllowedOverCurrentConnection() const;
+
+  // Global system context.
+  SystemState* system_state_;
+
+  // Contains state that is relevant in the processing of the Omaha request.
+  OmahaRequestParams* params_;
+
+  // Pointer to the OmahaEvent info. This is an UpdateCheck request if null.
+  std::unique_ptr<OmahaEvent> event_;
+
+  // pointer to the HttpFetcher that does the http work
+  std::unique_ptr<HttpFetcher> http_fetcher_;
+
+  // If true, only include the <ping> element in the request.
+  bool ping_only_;
+
+  // Stores the response from the omaha server
+  brillo::Blob response_buffer_;
+
+  // Initialized by InitPingDays to values that may be sent to Omaha
+  // as part of a ping message. Note that only positive values and -1
+  // are sent to Omaha.
+  int ping_active_days_;
+  int ping_roll_call_days_;
+
+  DISALLOW_COPY_AND_ASSIGN(OmahaRequestAction);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_OMAHA_REQUEST_ACTION_H_
diff --git a/omaha_request_action_unittest.cc b/omaha_request_action_unittest.cc
new file mode 100644
index 0000000..69585c8
--- /dev/null
+++ b/omaha_request_action_unittest.cc
@@ -0,0 +1,2176 @@
+//
+// Copyright (C) 2012 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 "update_engine/omaha_request_action.h"
+
+#include <stdint.h>
+
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/files/file_util.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/action_pipe.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/mock_http_fetcher.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/metrics.h"
+#include "update_engine/mock_connection_manager.h"
+#include "update_engine/mock_payload_state.h"
+#include "update_engine/omaha_request_params.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::test_utils::System;
+using chromeos_update_engine::test_utils::WriteFileString;
+using std::string;
+using std::vector;
+using testing::AllOf;
+using testing::AnyNumber;
+using testing::DoAll;
+using testing::Ge;
+using testing::Le;
+using testing::NiceMock;
+using testing::Return;
+using testing::ReturnPointee;
+using testing::SaveArg;
+using testing::SetArgumentPointee;
+using testing::_;
+
+namespace {
+
+const char kTestAppId[] = "test-app-id";
+
+// This is a helper struct to allow unit tests build an update response with the
+// values they care about.
+struct FakeUpdateResponse {
+  string GetNoUpdateResponse() const {
+    string entity_str;
+    if (include_entity)
+      entity_str = "<!DOCTYPE response [<!ENTITY CrOS \"ChromeOS\">]>";
+    return
+        "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" +
+        entity_str + "<response protocol=\"3.0\">"
+        "<daystart elapsed_seconds=\"100\"/>"
+        "<app appid=\"" + app_id + "\" " +
+        (include_cohorts ? "cohort=\"" + cohort + "\" cohorthint=\"" +
+         cohorthint + "\" cohortname=\"" + cohortname + "\" " : "") +
+        " status=\"ok\">"
+        "<ping status=\"ok\"/>"
+        "<updatecheck status=\"noupdate\"/></app></response>";
+  }
+
+  string GetUpdateResponse() const {
+    return
+        "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response "
+        "protocol=\"3.0\">"
+        "<daystart elapsed_seconds=\"100\"" +
+        (elapsed_days.empty() ? "" : (" elapsed_days=\"" + elapsed_days + "\""))
+        + "/>"
+        "<app appid=\"" + app_id + "\" " +
+        (include_cohorts ? "cohort=\"" + cohort + "\" cohorthint=\"" +
+         cohorthint + "\" cohortname=\"" + cohortname + "\" " : "") +
+        " status=\"ok\">"
+        "<ping status=\"ok\"/><updatecheck status=\"ok\">"
+        "<urls><url codebase=\"" + codebase + "\"/></urls>"
+        "<manifest version=\"" + version + "\">"
+        "<packages><package hash=\"not-used\" name=\"" + filename +  "\" "
+        "size=\"" + base::Int64ToString(size) + "\"/></packages>"
+        "<actions><action event=\"postinstall\" "
+        "ChromeOSVersion=\"" + version + "\" "
+        "MoreInfo=\"" + more_info_url + "\" Prompt=\"" + prompt + "\" "
+        "IsDelta=\"true\" "
+        "IsDeltaPayload=\"true\" "
+        "MaxDaysToScatter=\"" + max_days_to_scatter + "\" "
+        "sha256=\"" + hash + "\" "
+        "needsadmin=\"" + needsadmin + "\" " +
+        (deadline.empty() ? "" : ("deadline=\"" + deadline + "\" ")) +
+        (disable_p2p_for_downloading ?
+            "DisableP2PForDownloading=\"true\" " : "") +
+        (disable_p2p_for_sharing ? "DisableP2PForSharing=\"true\" " : "") +
+        "/></actions></manifest></updatecheck></app></response>";
+  }
+
+  // Return the payload URL, which is split in two fields in the XML response.
+  string GetPayloadUrl() {
+    return codebase + filename;
+  }
+
+  string app_id = kTestAppId;
+  string version = "1.2.3.4";
+  string more_info_url = "http://more/info";
+  string prompt = "true";
+  string codebase = "http://code/base/";
+  string filename = "file.signed";
+  string hash = "HASH1234=";
+  string needsadmin = "false";
+  int64_t size = 123;
+  string deadline = "";
+  string max_days_to_scatter = "7";
+  string elapsed_days = "42";
+
+  // P2P setting defaults to allowed.
+  bool disable_p2p_for_downloading = false;
+  bool disable_p2p_for_sharing = false;
+
+  // Omaha cohorts settings.
+  bool include_cohorts = false;
+  string cohort = "";
+  string cohorthint = "";
+  string cohortname = "";
+
+  // Whether to include the CrOS <!ENTITY> in the XML response.
+  bool include_entity = false;
+};
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+class OmahaRequestActionTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    fake_system_state_.set_request_params(&request_params_);
+    fake_system_state_.set_prefs(&fake_prefs_);
+  }
+
+  // Returns true iff an output response was obtained from the
+  // OmahaRequestAction. |prefs| may be null, in which case a local MockPrefs
+  // is used. |payload_state| may be null, in which case a local mock is used.
+  // |p2p_manager| may be null, in which case a local mock is used.
+  // |connection_manager| may be null, in which case a local mock is used.
+  // out_response may be null. If |fail_http_response_code| is non-negative,
+  // the transfer will fail with that code. |ping_only| is passed through to the
+  // OmahaRequestAction constructor. out_post_data may be null; if non-null, the
+  // post-data received by the mock HttpFetcher is returned.
+  //
+  // The |expected_check_result|, |expected_check_reaction| and
+  // |expected_error_code| parameters are for checking expectations
+  // about reporting UpdateEngine.Check.{Result,Reaction,DownloadError}
+  // UMA statistics. Use the appropriate ::kUnset value to specify that
+  // the given metric should not be reported.
+  bool TestUpdateCheck(OmahaRequestParams* request_params,
+                       const string& http_response,
+                       int fail_http_response_code,
+                       bool ping_only,
+                       ErrorCode expected_code,
+                       metrics::CheckResult expected_check_result,
+                       metrics::CheckReaction expected_check_reaction,
+                       metrics::DownloadErrorCode expected_download_error_code,
+                       OmahaResponse* out_response,
+                       brillo::Blob* out_post_data);
+
+  // Runs and checks a ping test. |ping_only| indicates whether it should send
+  // only a ping or also an updatecheck.
+  void PingTest(bool ping_only);
+
+  // InstallDate test helper function.
+  bool InstallDateParseHelper(const string &elapsed_days,
+                              OmahaResponse *response);
+
+  // P2P test helper function.
+  void P2PTest(
+      bool initial_allow_p2p_for_downloading,
+      bool initial_allow_p2p_for_sharing,
+      bool omaha_disable_p2p_for_downloading,
+      bool omaha_disable_p2p_for_sharing,
+      bool payload_state_allow_p2p_attempt,
+      bool expect_p2p_client_lookup,
+      const string& p2p_client_result_url,
+      bool expected_allow_p2p_for_downloading,
+      bool expected_allow_p2p_for_sharing,
+      const string& expected_p2p_url);
+
+  FakeSystemState fake_system_state_;
+  FakeUpdateResponse fake_update_response_;
+
+  // By default, all tests use these objects unless they replace them in the
+  // fake_system_state_.
+  OmahaRequestParams request_params_ = OmahaRequestParams{
+      &fake_system_state_,
+      constants::kOmahaPlatformName,
+      OmahaRequestParams::kOsVersion,
+      "service_pack",
+      "x86-generic",
+      kTestAppId,
+      "0.1.0.0",
+      "en-US",
+      "unittest",
+      "OEM MODEL 09235 7471",
+      "ChromeOSFirmware.1.0",
+      "0X0A1",
+      false,   // delta okay
+      false,   // interactive
+      "http://url",
+      ""};     // target_version_prefix
+
+  FakePrefs fake_prefs_;
+};
+
+namespace {
+class OmahaRequestActionTestProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  OmahaRequestActionTestProcessorDelegate()
+      : expected_code_(ErrorCode::kSuccess) {}
+  ~OmahaRequestActionTestProcessorDelegate() override {
+  }
+  void ProcessingDone(const ActionProcessor* processor,
+                      ErrorCode code) override {
+    brillo::MessageLoop::current()->BreakLoop();
+  }
+
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) override {
+    // make sure actions always succeed
+    if (action->Type() == OmahaRequestAction::StaticType())
+      EXPECT_EQ(expected_code_, code);
+    else
+      EXPECT_EQ(ErrorCode::kSuccess, code);
+  }
+  ErrorCode expected_code_;
+};
+}  // namespace
+
+class OutputObjectCollectorAction;
+
+template<>
+class ActionTraits<OutputObjectCollectorAction> {
+ public:
+  // Does not take an object for input
+  typedef OmahaResponse InputObjectType;
+  // On success, puts the output path on output
+  typedef NoneType OutputObjectType;
+};
+
+class OutputObjectCollectorAction : public Action<OutputObjectCollectorAction> {
+ public:
+  OutputObjectCollectorAction() : has_input_object_(false) {}
+  void PerformAction() {
+    // copy input object
+    has_input_object_ = HasInputObject();
+    if (has_input_object_)
+      omaha_response_ = GetInputObject();
+    processor_->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  // Should never be called
+  void TerminateProcessing() {
+    CHECK(false);
+  }
+  // Debugging/logging
+  static string StaticType() {
+    return "OutputObjectCollectorAction";
+  }
+  string Type() const { return StaticType(); }
+  bool has_input_object_;
+  OmahaResponse omaha_response_;
+};
+
+bool OmahaRequestActionTest::TestUpdateCheck(
+    OmahaRequestParams* request_params,
+    const string& http_response,
+    int fail_http_response_code,
+    bool ping_only,
+    ErrorCode expected_code,
+    metrics::CheckResult expected_check_result,
+    metrics::CheckReaction expected_check_reaction,
+    metrics::DownloadErrorCode expected_download_error_code,
+    OmahaResponse* out_response,
+    brillo::Blob* out_post_data) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+  MockHttpFetcher* fetcher = new MockHttpFetcher(http_response.data(),
+                                                 http_response.size(),
+                                                 nullptr);
+  if (fail_http_response_code >= 0) {
+    fetcher->FailTransfer(fail_http_response_code);
+  }
+  if (request_params)
+    fake_system_state_.set_request_params(request_params);
+  OmahaRequestAction action(&fake_system_state_,
+                            nullptr,
+                            brillo::make_unique_ptr(fetcher),
+                            ping_only);
+  OmahaRequestActionTestProcessorDelegate delegate;
+  delegate.expected_code_ = expected_code;
+
+  ActionProcessor processor;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&action);
+
+  OutputObjectCollectorAction collector_action;
+  BondActions(&action, &collector_action);
+  processor.EnqueueAction(&collector_action);
+
+  EXPECT_CALL(*fake_system_state_.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+      .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state_.mock_metrics_lib(),
+      SendEnumToUMA(metrics::kMetricCheckResult,
+          static_cast<int>(expected_check_result),
+          static_cast<int>(metrics::CheckResult::kNumConstants) - 1))
+      .Times(expected_check_result == metrics::CheckResult::kUnset ? 0 : 1);
+  EXPECT_CALL(*fake_system_state_.mock_metrics_lib(),
+      SendEnumToUMA(metrics::kMetricCheckReaction,
+          static_cast<int>(expected_check_reaction),
+          static_cast<int>(metrics::CheckReaction::kNumConstants) - 1))
+      .Times(expected_check_reaction == metrics::CheckReaction::kUnset ? 0 : 1);
+  EXPECT_CALL(*fake_system_state_.mock_metrics_lib(),
+      SendSparseToUMA(metrics::kMetricCheckDownloadErrorCode,
+          static_cast<int>(expected_download_error_code)))
+      .Times(expected_download_error_code == metrics::DownloadErrorCode::kUnset
+             ? 0 : 1);
+
+  loop.PostTask(base::Bind([&processor] { processor.StartProcessing(); }));
+  LOG(INFO) << "loop.PendingTasks() = " << loop.PendingTasks();
+  loop.Run();
+  LOG(INFO) << "loop.PendingTasks() = " << loop.PendingTasks();
+  EXPECT_FALSE(loop.PendingTasks());
+  if (collector_action.has_input_object_ && out_response)
+    *out_response = collector_action.omaha_response_;
+  if (out_post_data)
+    *out_post_data = fetcher->post_data();
+  return collector_action.has_input_object_;
+}
+
+// Tests Event requests -- they should always succeed. |out_post_data|
+// may be null; if non-null, the post-data received by the mock
+// HttpFetcher is returned.
+void TestEvent(OmahaRequestParams params,
+               OmahaEvent* event,
+               const string& http_response,
+               brillo::Blob* out_post_data) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+  MockHttpFetcher* fetcher = new MockHttpFetcher(http_response.data(),
+                                                 http_response.size(),
+                                                 nullptr);
+  FakeSystemState fake_system_state;
+  fake_system_state.set_request_params(&params);
+  OmahaRequestAction action(&fake_system_state,
+                            event,
+                            brillo::make_unique_ptr(fetcher),
+                            false);
+  OmahaRequestActionTestProcessorDelegate delegate;
+  ActionProcessor processor;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&action);
+
+  loop.PostTask(base::Bind([&processor] { processor.StartProcessing(); }));
+  loop.Run();
+
+  // This test should schedule a callback to notify the crash reporter if
+  // the passed event is an error.
+  EXPECT_EQ(event->result == OmahaEvent::kResultError, loop.PendingTasks());
+
+  if (out_post_data)
+    *out_post_data = fetcher->post_data();
+}
+
+TEST_F(OmahaRequestActionTest, RejectEntities) {
+  OmahaResponse response;
+  fake_update_response_.include_entity = true;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaRequestXMLHasEntityDecl,
+                      metrics::CheckResult::kParsingError,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, NoUpdateTest) {
+  OmahaResponse response;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+// Test that all the values in the response are parsed in a normal update
+// response.
+TEST_F(OmahaRequestActionTest, ValidUpdateTest) {
+  OmahaResponse response;
+  fake_update_response_.deadline = "20101020";
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ(fake_update_response_.version, response.version);
+  EXPECT_EQ(fake_update_response_.GetPayloadUrl(), response.payload_urls[0]);
+  EXPECT_EQ(fake_update_response_.more_info_url, response.more_info_url);
+  EXPECT_EQ(fake_update_response_.hash, response.hash);
+  EXPECT_EQ(fake_update_response_.size, response.size);
+  EXPECT_EQ(fake_update_response_.prompt == "true", response.prompt);
+  EXPECT_EQ(fake_update_response_.deadline, response.deadline);
+  // Omaha cohort attribets are not set in the response, so they should not be
+  // persisted.
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsOmahaCohort));
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsOmahaCohortHint));
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsOmahaCohortName));
+}
+
+TEST_F(OmahaRequestActionTest, ValidUpdateBlockedByConnection) {
+  OmahaResponse response;
+  // Set up a connection manager that doesn't allow a valid update over
+  // the current ethernet connection.
+  MockConnectionManager mock_cm;
+  fake_system_state_.set_connection_manager(&mock_cm);
+
+  EXPECT_CALL(mock_cm, GetConnectionProperties(_, _))
+      .WillRepeatedly(
+          DoAll(SetArgumentPointee<0>(NetworkConnectionType::kEthernet),
+                SetArgumentPointee<1>(NetworkTethering::kUnknown),
+                Return(true)));
+  EXPECT_CALL(mock_cm, IsUpdateAllowedOver(NetworkConnectionType::kEthernet, _))
+    .WillRepeatedly(Return(false));
+
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateIgnoredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kIgnored,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, ValidUpdateBlockedByRollback) {
+  string rollback_version = "1234.0.0";
+  OmahaResponse response;
+
+  MockPayloadState mock_payload_state;
+  fake_system_state_.set_payload_state(&mock_payload_state);
+
+  EXPECT_CALL(mock_payload_state, GetRollbackVersion())
+    .WillRepeatedly(Return(rollback_version));
+
+  fake_update_response_.version = rollback_version;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateIgnoredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kIgnored,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, WallClockBasedWaitAloneCausesScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_update_check_count_wait_enabled(false);
+  params.set_waiting_period(TimeDelta::FromDays(2));
+
+  ASSERT_FALSE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateDeferredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kDeferring,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+
+  // Verify if we are interactive check we don't defer.
+  params.set_interactive(true);
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, NoWallClockBasedWaitCausesNoScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(false);
+  params.set_waiting_period(TimeDelta::FromDays(2));
+
+  params.set_update_check_count_wait_enabled(true);
+  params.set_min_update_checks_needed(1);
+  params.set_max_update_checks_allowed(8);
+
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, ZeroMaxDaysToScatterCausesNoScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta::FromDays(2));
+
+  params.set_update_check_count_wait_enabled(true);
+  params.set_min_update_checks_needed(1);
+  params.set_max_update_checks_allowed(8);
+
+  fake_update_response_.max_days_to_scatter = "0";
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+
+TEST_F(OmahaRequestActionTest, ZeroUpdateCheckCountCausesNoScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta());
+
+  params.set_update_check_count_wait_enabled(true);
+  params.set_min_update_checks_needed(0);
+  params.set_max_update_checks_allowed(0);
+
+  ASSERT_TRUE(TestUpdateCheck(
+                      &params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  int64_t count;
+  ASSERT_TRUE(fake_prefs_.GetInt64(kPrefsUpdateCheckCount, &count));
+  ASSERT_EQ(count, 0);
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, NonZeroUpdateCheckCountCausesScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta());
+
+  params.set_update_check_count_wait_enabled(true);
+  params.set_min_update_checks_needed(1);
+  params.set_max_update_checks_allowed(8);
+
+  ASSERT_FALSE(TestUpdateCheck(
+                      &params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateDeferredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kDeferring,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  int64_t count;
+  ASSERT_TRUE(fake_prefs_.GetInt64(kPrefsUpdateCheckCount, &count));
+  ASSERT_GT(count, 0);
+  EXPECT_FALSE(response.update_exists);
+
+  // Verify if we are interactive check we don't defer.
+  params.set_interactive(true);
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, ExistingUpdateCheckCountCausesScattering) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta());
+
+  params.set_update_check_count_wait_enabled(true);
+  params.set_min_update_checks_needed(1);
+  params.set_max_update_checks_allowed(8);
+
+  ASSERT_TRUE(fake_prefs_.SetInt64(kPrefsUpdateCheckCount, 5));
+
+  ASSERT_FALSE(TestUpdateCheck(
+                      &params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateDeferredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kDeferring,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  int64_t count;
+  ASSERT_TRUE(fake_prefs_.GetInt64(kPrefsUpdateCheckCount, &count));
+  // count remains the same, as the decrementing happens in update_attempter
+  // which this test doesn't exercise.
+  ASSERT_EQ(count, 5);
+  EXPECT_FALSE(response.update_exists);
+
+  // Verify if we are interactive check we don't defer.
+  params.set_interactive(true);
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, CohortsArePersisted) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  fake_update_response_.include_cohorts = true;
+  fake_update_response_.cohort = "s/154454/8479665";
+  fake_update_response_.cohorthint = "please-put-me-on-beta";
+  fake_update_response_.cohortname = "stable";
+
+  ASSERT_TRUE(TestUpdateCheck(&params,
+                              fake_update_response_.GetUpdateResponse(),
+                              -1,
+                              false,  // ping_only
+                              ErrorCode::kSuccess,
+                              metrics::CheckResult::kUpdateAvailable,
+                              metrics::CheckReaction::kUpdating,
+                              metrics::DownloadErrorCode::kUnset,
+                              &response,
+                              nullptr));
+
+  string value;
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohort, &value));
+  EXPECT_EQ(fake_update_response_.cohort, value);
+
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohortHint, &value));
+  EXPECT_EQ(fake_update_response_.cohorthint, value);
+
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohortName, &value));
+  EXPECT_EQ(fake_update_response_.cohortname, value);
+}
+
+TEST_F(OmahaRequestActionTest, CohortsAreUpdated) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  EXPECT_TRUE(fake_prefs_.SetString(kPrefsOmahaCohort, "old_value"));
+  EXPECT_TRUE(fake_prefs_.SetString(kPrefsOmahaCohortHint, "old_hint"));
+  EXPECT_TRUE(fake_prefs_.SetString(kPrefsOmahaCohortName, "old_name"));
+  fake_update_response_.include_cohorts = true;
+  fake_update_response_.cohort = "s/154454/8479665";
+  fake_update_response_.cohorthint = "please-put-me-on-beta";
+  fake_update_response_.cohortname = "";
+
+  ASSERT_TRUE(TestUpdateCheck(&params,
+                              fake_update_response_.GetUpdateResponse(),
+                              -1,
+                              false,  // ping_only
+                              ErrorCode::kSuccess,
+                              metrics::CheckResult::kUpdateAvailable,
+                              metrics::CheckReaction::kUpdating,
+                              metrics::DownloadErrorCode::kUnset,
+                              &response,
+                              nullptr));
+
+  string value;
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohort, &value));
+  EXPECT_EQ(fake_update_response_.cohort, value);
+
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohortHint, &value));
+  EXPECT_EQ(fake_update_response_.cohorthint, value);
+
+  EXPECT_FALSE(fake_prefs_.GetString(kPrefsOmahaCohortName, &value));
+}
+
+TEST_F(OmahaRequestActionTest, CohortsAreNotModifiedWhenMissing) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  EXPECT_TRUE(fake_prefs_.SetString(kPrefsOmahaCohort, "old_value"));
+
+  ASSERT_TRUE(TestUpdateCheck(&params,
+                              fake_update_response_.GetUpdateResponse(),
+                              -1,
+                              false,  // ping_only
+                              ErrorCode::kSuccess,
+                              metrics::CheckResult::kUpdateAvailable,
+                              metrics::CheckReaction::kUpdating,
+                              metrics::DownloadErrorCode::kUnset,
+                              &response,
+                              nullptr));
+
+  string value;
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohort, &value));
+  EXPECT_EQ("old_value", value);
+
+  EXPECT_FALSE(fake_prefs_.GetString(kPrefsOmahaCohortHint, &value));
+  EXPECT_FALSE(fake_prefs_.GetString(kPrefsOmahaCohortName, &value));
+}
+
+TEST_F(OmahaRequestActionTest, CohortsArePersistedWhenNoUpdate) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  fake_update_response_.include_cohorts = true;
+  fake_update_response_.cohort = "s/154454/8479665";
+  fake_update_response_.cohorthint = "please-put-me-on-beta";
+  fake_update_response_.cohortname = "stable";
+
+  ASSERT_TRUE(TestUpdateCheck(&params,
+                              fake_update_response_.GetNoUpdateResponse(),
+                              -1,
+                              false,  // ping_only
+                              ErrorCode::kSuccess,
+                              metrics::CheckResult::kNoUpdateAvailable,
+                              metrics::CheckReaction::kUnset,
+                              metrics::DownloadErrorCode::kUnset,
+                              &response,
+                              nullptr));
+
+  string value;
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohort, &value));
+  EXPECT_EQ(fake_update_response_.cohort, value);
+
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohortHint, &value));
+  EXPECT_EQ(fake_update_response_.cohorthint, value);
+
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsOmahaCohortName, &value));
+  EXPECT_EQ(fake_update_response_.cohortname, value);
+}
+
+TEST_F(OmahaRequestActionTest, NoOutputPipeTest) {
+  const string http_response(fake_update_response_.GetNoUpdateResponse());
+
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+
+  OmahaRequestParams params = request_params_;
+  fake_system_state_.set_request_params(&params);
+  OmahaRequestAction action(&fake_system_state_, nullptr,
+                            brillo::make_unique_ptr(
+                                new MockHttpFetcher(http_response.data(),
+                                                    http_response.size(),
+                                                    nullptr)),
+                            false);
+  OmahaRequestActionTestProcessorDelegate delegate;
+  ActionProcessor processor;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&action);
+
+  loop.PostTask(base::Bind([&processor] { processor.StartProcessing(); }));
+  loop.Run();
+  EXPECT_FALSE(loop.PendingTasks());
+  EXPECT_FALSE(processor.IsRunning());
+}
+
+TEST_F(OmahaRequestActionTest, InvalidXmlTest) {
+  OmahaResponse response;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "invalid xml>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaRequestXMLParseError,
+                      metrics::CheckResult::kParsingError,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, EmptyResponseTest) {
+  OmahaResponse response;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaRequestEmptyResponseError,
+                      metrics::CheckResult::kParsingError,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, MissingStatusTest) {
+  OmahaResponse response;
+  ASSERT_FALSE(TestUpdateCheck(
+      nullptr,  // request_params
+      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response protocol=\"3.0\">"
+      "<daystart elapsed_seconds=\"100\"/>"
+      "<app appid=\"foo\" status=\"ok\">"
+      "<ping status=\"ok\"/>"
+      "<updatecheck/></app></response>",
+      -1,
+      false,  // ping_only
+      ErrorCode::kOmahaResponseInvalid,
+      metrics::CheckResult::kParsingError,
+      metrics::CheckReaction::kUnset,
+      metrics::DownloadErrorCode::kUnset,
+      &response,
+      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, InvalidStatusTest) {
+  OmahaResponse response;
+  ASSERT_FALSE(TestUpdateCheck(
+      nullptr,  // request_params
+      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response protocol=\"3.0\">"
+      "<daystart elapsed_seconds=\"100\"/>"
+      "<app appid=\"foo\" status=\"ok\">"
+      "<ping status=\"ok\"/>"
+      "<updatecheck status=\"InvalidStatusTest\"/></app></response>",
+      -1,
+      false,  // ping_only
+      ErrorCode::kOmahaResponseInvalid,
+      metrics::CheckResult::kParsingError,
+      metrics::CheckReaction::kUnset,
+      metrics::DownloadErrorCode::kUnset,
+      &response,
+      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, MissingNodesetTest) {
+  OmahaResponse response;
+  ASSERT_FALSE(TestUpdateCheck(
+      nullptr,  // request_params
+      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response protocol=\"3.0\">"
+      "<daystart elapsed_seconds=\"100\"/>"
+      "<app appid=\"foo\" status=\"ok\">"
+      "<ping status=\"ok\"/>"
+      "</app></response>",
+      -1,
+      false,  // ping_only
+      ErrorCode::kOmahaResponseInvalid,
+      metrics::CheckResult::kParsingError,
+      metrics::CheckReaction::kUnset,
+      metrics::DownloadErrorCode::kUnset,
+      &response,
+      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, MissingFieldTest) {
+  string input_response =
+      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response protocol=\"3.0\">"
+      "<daystart elapsed_seconds=\"100\"/>"
+      "<app appid=\"xyz\" status=\"ok\">"
+      "<updatecheck status=\"ok\">"
+      "<urls><url codebase=\"http://missing/field/test/\"/></urls>"
+      "<manifest version=\"10.2.3.4\">"
+      "<packages><package hash=\"not-used\" name=\"f\" "
+      "size=\"587\"/></packages>"
+      "<actions><action event=\"postinstall\" "
+      "ChromeOSVersion=\"10.2.3.4\" "
+      "Prompt=\"false\" "
+      "IsDelta=\"true\" "
+      "IsDeltaPayload=\"false\" "
+      "sha256=\"lkq34j5345\" "
+      "needsadmin=\"true\" "
+      "/></actions></manifest></updatecheck></app></response>";
+  LOG(INFO) << "Input Response = " << input_response;
+
+  OmahaResponse response;
+  ASSERT_TRUE(TestUpdateCheck(nullptr,  // request_params
+                              input_response,
+                              -1,
+                              false,  // ping_only
+                              ErrorCode::kSuccess,
+                              metrics::CheckResult::kUpdateAvailable,
+                              metrics::CheckReaction::kUpdating,
+                              metrics::DownloadErrorCode::kUnset,
+                              &response,
+                              nullptr));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ("10.2.3.4", response.version);
+  EXPECT_EQ("http://missing/field/test/f", response.payload_urls[0]);
+  EXPECT_EQ("", response.more_info_url);
+  EXPECT_EQ("lkq34j5345", response.hash);
+  EXPECT_EQ(587, response.size);
+  EXPECT_FALSE(response.prompt);
+  EXPECT_TRUE(response.deadline.empty());
+}
+
+namespace {
+class TerminateEarlyTestProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  void ProcessingStopped(const ActionProcessor* processor) {
+    brillo::MessageLoop::current()->BreakLoop();
+  }
+};
+
+void TerminateTransferTestStarter(ActionProcessor* processor) {
+  processor->StartProcessing();
+  CHECK(processor->IsRunning());
+  processor->StopProcessing();
+}
+}  // namespace
+
+TEST_F(OmahaRequestActionTest, TerminateTransferTest) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+
+  string http_response("doesn't matter");
+  OmahaRequestAction action(&fake_system_state_, nullptr,
+                            brillo::make_unique_ptr(
+                                new MockHttpFetcher(http_response.data(),
+                                                    http_response.size(),
+                                                    nullptr)),
+                            false);
+  TerminateEarlyTestProcessorDelegate delegate;
+  ActionProcessor processor;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&action);
+
+  loop.PostTask(base::Bind(&TerminateTransferTestStarter, &processor));
+  loop.Run();
+  EXPECT_FALSE(loop.PendingTasks());
+}
+
+TEST_F(OmahaRequestActionTest, XmlEncodeTest) {
+  string output;
+  EXPECT_TRUE(XmlEncode("ab", &output));
+  EXPECT_EQ("ab", output);
+  EXPECT_TRUE(XmlEncode("a<b", &output));
+  EXPECT_EQ("a&lt;b", output);
+  EXPECT_TRUE(XmlEncode("<&>\"\'\\", &output));
+  EXPECT_EQ("&lt;&amp;&gt;&quot;&apos;\\", output);
+  EXPECT_TRUE(XmlEncode("&lt;&amp;&gt;", &output));
+  EXPECT_EQ("&amp;lt;&amp;amp;&amp;gt;", output);
+  // Check that unterminated UTF-8 strings are handled properly.
+  EXPECT_FALSE(XmlEncode("\xc2", &output));
+  // Fail with invalid ASCII-7 chars.
+  EXPECT_FALSE(XmlEncode("This is an 'n' with a tilde: \xc3\xb1", &output));
+}
+
+TEST_F(OmahaRequestActionTest, XmlEncodeWithDefaultTest) {
+  EXPECT_EQ("&lt;&amp;&gt;", XmlEncodeWithDefault("<&>", "something else"));
+  EXPECT_EQ("<not escaped>", XmlEncodeWithDefault("\xc2", "<not escaped>"));
+}
+
+TEST_F(OmahaRequestActionTest, XmlEncodeIsUsedForParams) {
+  brillo::Blob post_data;
+
+  // Make sure XML Encode is being called on the params
+  OmahaRequestParams params(&fake_system_state_,
+                            constants::kOmahaPlatformName,
+                            OmahaRequestParams::kOsVersion,
+                            "testtheservice_pack>",
+                            "x86 generic<id",
+                            kTestAppId,
+                            "0.1.0.0",
+                            "en-US",
+                            "unittest_track&lt;",
+                            "<OEM MODEL>",
+                            "ChromeOSFirmware.1.0",
+                            "EC100",
+                            false,   // delta okay
+                            false,   // interactive
+                            "http://url",
+                            "");     // target_version_prefix
+  fake_prefs_.SetString(kPrefsOmahaCohort, "evil\nstring");
+  fake_prefs_.SetString(kPrefsOmahaCohortHint, "evil&string\\");
+  fake_prefs_.SetString(kPrefsOmahaCohortName,
+                        JoinString(vector<string>(100, "My spoon is too big."),
+                                   ' '));
+  OmahaResponse response;
+  ASSERT_FALSE(
+      TestUpdateCheck(&params,
+                      "invalid xml>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaRequestXMLParseError,
+                      metrics::CheckResult::kParsingError,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      &post_data));
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(string::npos, post_str.find("testtheservice_pack&gt;"));
+  EXPECT_EQ(string::npos, post_str.find("testtheservice_pack>"));
+  EXPECT_NE(string::npos, post_str.find("x86 generic&lt;id"));
+  EXPECT_EQ(string::npos, post_str.find("x86 generic<id"));
+  EXPECT_NE(string::npos, post_str.find("unittest_track&amp;lt;"));
+  EXPECT_EQ(string::npos, post_str.find("unittest_track&lt;"));
+  EXPECT_NE(string::npos, post_str.find("&lt;OEM MODEL&gt;"));
+  EXPECT_EQ(string::npos, post_str.find("<OEM MODEL>"));
+  EXPECT_NE(string::npos, post_str.find("cohort=\"evil\nstring\""));
+  EXPECT_EQ(string::npos, post_str.find("cohorthint=\"evil&string\\\""));
+  EXPECT_NE(string::npos, post_str.find("cohorthint=\"evil&amp;string\\\""));
+  // Values from Prefs that are too big are removed from the XML instead of
+  // encoded.
+  EXPECT_EQ(string::npos, post_str.find("cohortname="));
+}
+
+TEST_F(OmahaRequestActionTest, XmlDecodeTest) {
+  OmahaResponse response;
+  fake_update_response_.deadline = "&lt;20110101";
+  fake_update_response_.more_info_url = "testthe&lt;url";
+  fake_update_response_.codebase = "testthe&amp;codebase/";
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  EXPECT_EQ(response.more_info_url, "testthe<url");
+  EXPECT_EQ(response.payload_urls[0], "testthe&codebase/file.signed");
+  EXPECT_EQ(response.deadline, "<20110101");
+}
+
+TEST_F(OmahaRequestActionTest, ParseIntTest) {
+  OmahaResponse response;
+  // overflows int32_t:
+  fake_update_response_.size = 123123123123123ll;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  EXPECT_EQ(response.size, 123123123123123ll);
+}
+
+TEST_F(OmahaRequestActionTest, FormatUpdateCheckOutputTest) {
+  brillo::Blob post_data;
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+
+  EXPECT_CALL(prefs, GetString(kPrefsPreviousVersion, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(string("")), Return(true)));
+  // An existing but empty previous version means that we didn't reboot to a new
+  // update, therefore, no need to update the previous version.
+  EXPECT_CALL(prefs, SetString(kPrefsPreviousVersion, _)).Times(0);
+  ASSERT_FALSE(TestUpdateCheck(nullptr,  // request_params
+                               "invalid xml>",
+                               -1,
+                               false,  // ping_only
+                               ErrorCode::kOmahaRequestXMLParseError,
+                               metrics::CheckResult::kParsingError,
+                               metrics::CheckReaction::kUnset,
+                               metrics::DownloadErrorCode::kUnset,
+                               nullptr,  // response
+                               &post_data));
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(post_str.find(
+      "        <ping active=\"1\" a=\"-1\" r=\"-1\"></ping>\n"
+      "        <updatecheck targetversionprefix=\"\"></updatecheck>\n"),
+      string::npos);
+  EXPECT_NE(post_str.find("hardware_class=\"OEM MODEL 09235 7471\""),
+            string::npos);
+  EXPECT_NE(post_str.find("fw_version=\"ChromeOSFirmware.1.0\""),
+            string::npos);
+  EXPECT_NE(post_str.find("ec_version=\"0X0A1\""),
+            string::npos);
+  // No <event> tag should be sent if we didn't reboot to an update.
+  EXPECT_EQ(post_str.find("<event"), string::npos);
+}
+
+
+TEST_F(OmahaRequestActionTest, FormatSuccessEventOutputTest) {
+  brillo::Blob post_data;
+  TestEvent(request_params_,
+            new OmahaEvent(OmahaEvent::kTypeUpdateDownloadStarted),
+            "invalid xml>",
+            &post_data);
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  string expected_event = base::StringPrintf(
+      "        <event eventtype=\"%d\" eventresult=\"%d\"></event>\n",
+      OmahaEvent::kTypeUpdateDownloadStarted,
+      OmahaEvent::kResultSuccess);
+  EXPECT_NE(post_str.find(expected_event), string::npos);
+  EXPECT_EQ(post_str.find("ping"), string::npos);
+  EXPECT_EQ(post_str.find("updatecheck"), string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, FormatErrorEventOutputTest) {
+  brillo::Blob post_data;
+  TestEvent(request_params_,
+            new OmahaEvent(OmahaEvent::kTypeDownloadComplete,
+                           OmahaEvent::kResultError,
+                           ErrorCode::kError),
+            "invalid xml>",
+            &post_data);
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  string expected_event = base::StringPrintf(
+      "        <event eventtype=\"%d\" eventresult=\"%d\" "
+      "errorcode=\"%d\"></event>\n",
+      OmahaEvent::kTypeDownloadComplete,
+      OmahaEvent::kResultError,
+      static_cast<int>(ErrorCode::kError));
+  EXPECT_NE(post_str.find(expected_event), string::npos);
+  EXPECT_EQ(post_str.find("updatecheck"), string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, IsEventTest) {
+  string http_response("doesn't matter");
+  // Create a copy of the OmahaRequestParams to reuse it later.
+  OmahaRequestParams params = request_params_;
+  fake_system_state_.set_request_params(&params);
+  OmahaRequestAction update_check_action(
+      &fake_system_state_,
+      nullptr,
+      brillo::make_unique_ptr(
+          new MockHttpFetcher(http_response.data(),
+                              http_response.size(),
+                              nullptr)),
+      false);
+  EXPECT_FALSE(update_check_action.IsEvent());
+
+  params = request_params_;
+  fake_system_state_.set_request_params(&params);
+  OmahaRequestAction event_action(
+      &fake_system_state_,
+      new OmahaEvent(OmahaEvent::kTypeUpdateComplete),
+      brillo::make_unique_ptr(
+          new MockHttpFetcher(http_response.data(),
+                              http_response.size(),
+                              nullptr)),
+      false);
+  EXPECT_TRUE(event_action.IsEvent());
+}
+
+TEST_F(OmahaRequestActionTest, FormatDeltaOkayOutputTest) {
+  for (int i = 0; i < 2; i++) {
+    bool delta_okay = i == 1;
+    const char* delta_okay_str = delta_okay ? "true" : "false";
+    brillo::Blob post_data;
+    OmahaRequestParams params(&fake_system_state_,
+                              constants::kOmahaPlatformName,
+                              OmahaRequestParams::kOsVersion,
+                              "service_pack",
+                              "x86-generic",
+                              kTestAppId,
+                              "0.1.0.0",
+                              "en-US",
+                              "unittest_track",
+                              "OEM MODEL REV 1234",
+                              "ChromeOSFirmware.1.0",
+                              "EC100",
+                              delta_okay,
+                              false,  // interactive
+                              "http://url",
+                              "");    // target_version_prefix
+    ASSERT_FALSE(TestUpdateCheck(&params,
+                                 "invalid xml>",
+                                 -1,
+                                 false,  // ping_only
+                                 ErrorCode::kOmahaRequestXMLParseError,
+                                 metrics::CheckResult::kParsingError,
+                                 metrics::CheckReaction::kUnset,
+                                 metrics::DownloadErrorCode::kUnset,
+                                 nullptr,
+                                 &post_data));
+    // convert post_data to string
+    string post_str(post_data.begin(), post_data.end());
+    EXPECT_NE(post_str.find(base::StringPrintf(" delta_okay=\"%s\"",
+                                               delta_okay_str)),
+              string::npos)
+        << "i = " << i;
+  }
+}
+
+TEST_F(OmahaRequestActionTest, FormatInteractiveOutputTest) {
+  for (int i = 0; i < 2; i++) {
+    bool interactive = i == 1;
+    const char* interactive_str = interactive ? "ondemandupdate" : "scheduler";
+    brillo::Blob post_data;
+    FakeSystemState fake_system_state;
+    OmahaRequestParams params(&fake_system_state_,
+                              constants::kOmahaPlatformName,
+                              OmahaRequestParams::kOsVersion,
+                              "service_pack",
+                              "x86-generic",
+                              kTestAppId,
+                              "0.1.0.0",
+                              "en-US",
+                              "unittest_track",
+                              "OEM MODEL REV 1234",
+                              "ChromeOSFirmware.1.0",
+                              "EC100",
+                              true,   // delta_okay
+                              interactive,
+                              "http://url",
+                              "");    // target_version_prefix
+    ASSERT_FALSE(TestUpdateCheck(&params,
+                                 "invalid xml>",
+                                 -1,
+                                 false,  // ping_only
+                                 ErrorCode::kOmahaRequestXMLParseError,
+                                 metrics::CheckResult::kParsingError,
+                                 metrics::CheckReaction::kUnset,
+                                 metrics::DownloadErrorCode::kUnset,
+                                 nullptr,
+                                 &post_data));
+    // convert post_data to string
+    string post_str(post_data.begin(), post_data.end());
+    EXPECT_NE(post_str.find(base::StringPrintf("installsource=\"%s\"",
+                                               interactive_str)),
+              string::npos)
+        << "i = " << i;
+  }
+}
+
+TEST_F(OmahaRequestActionTest, OmahaEventTest) {
+  OmahaEvent default_event;
+  EXPECT_EQ(OmahaEvent::kTypeUnknown, default_event.type);
+  EXPECT_EQ(OmahaEvent::kResultError, default_event.result);
+  EXPECT_EQ(ErrorCode::kError, default_event.error_code);
+
+  OmahaEvent success_event(OmahaEvent::kTypeUpdateDownloadStarted);
+  EXPECT_EQ(OmahaEvent::kTypeUpdateDownloadStarted, success_event.type);
+  EXPECT_EQ(OmahaEvent::kResultSuccess, success_event.result);
+  EXPECT_EQ(ErrorCode::kSuccess, success_event.error_code);
+
+  OmahaEvent error_event(OmahaEvent::kTypeUpdateDownloadFinished,
+                         OmahaEvent::kResultError,
+                         ErrorCode::kError);
+  EXPECT_EQ(OmahaEvent::kTypeUpdateDownloadFinished, error_event.type);
+  EXPECT_EQ(OmahaEvent::kResultError, error_event.result);
+  EXPECT_EQ(ErrorCode::kError, error_event.error_code);
+}
+
+void OmahaRequestActionTest::PingTest(bool ping_only) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(kPrefsMetricsCheckLastReportingTime, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  // Add a few hours to the day difference to test no rounding, etc.
+  int64_t five_days_ago =
+      (Time::Now() - TimeDelta::FromHours(5 * 24 + 13)).ToInternalValue();
+  int64_t six_days_ago =
+      (Time::Now() - TimeDelta::FromHours(6 * 24 + 11)).ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsInstallDateDays, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(0), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(six_days_ago), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(five_days_ago), Return(true)));
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      ping_only,
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUnset,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(post_str.find("<ping active=\"1\" a=\"6\" r=\"5\"></ping>"),
+            string::npos);
+  if (ping_only) {
+    EXPECT_EQ(post_str.find("updatecheck"), string::npos);
+    EXPECT_EQ(post_str.find("previousversion"), string::npos);
+  } else {
+    EXPECT_NE(post_str.find("updatecheck"), string::npos);
+    EXPECT_NE(post_str.find("previousversion"), string::npos);
+  }
+}
+
+TEST_F(OmahaRequestActionTest, PingTestSendOnlyAPing) {
+  PingTest(true  /* ping_only */);
+}
+
+TEST_F(OmahaRequestActionTest, PingTestSendAlsoAnUpdateCheck) {
+  PingTest(false  /* ping_only */);
+}
+
+TEST_F(OmahaRequestActionTest, ActivePingTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(kPrefsMetricsCheckLastReportingTime, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  int64_t three_days_ago =
+      (Time::Now() - TimeDelta::FromHours(3 * 24 + 12)).ToInternalValue();
+  int64_t now = Time::Now().ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsInstallDateDays, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(0), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(three_days_ago), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(now), Return(true)));
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(post_str.find("<ping active=\"1\" a=\"3\"></ping>"),
+            string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, RollCallPingTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(kPrefsMetricsCheckLastReportingTime, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  int64_t four_days_ago =
+      (Time::Now() - TimeDelta::FromHours(4 * 24)).ToInternalValue();
+  int64_t now = Time::Now().ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsInstallDateDays, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(0), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(now), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(four_days_ago), Return(true)));
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(post_str.find("<ping active=\"1\" r=\"4\"></ping>\n"),
+            string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, NoPingTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(kPrefsMetricsCheckLastReportingTime, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  int64_t one_hour_ago =
+      (Time::Now() - TimeDelta::FromHours(1)).ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsInstallDateDays, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(0), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(one_hour_ago), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(one_hour_ago), Return(true)));
+  // LastActivePingDay and PrefsLastRollCallPingDay are set even if we didn't
+  // send a ping.
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(Return(true));
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(Return(true));
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_EQ(post_str.find("ping"), string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, IgnoreEmptyPingTest) {
+  // This test ensures that we ignore empty ping only requests.
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  int64_t now = Time::Now().ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(now), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(now), Return(true)));
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay, _)).Times(0);
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay, _)).Times(0);
+  brillo::Blob post_data;
+  EXPECT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      true,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUnset,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  EXPECT_EQ(post_data.size(), 0);
+}
+
+TEST_F(OmahaRequestActionTest, BackInTimePingTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(kPrefsMetricsCheckLastReportingTime, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  int64_t future =
+      (Time::Now() + TimeDelta::FromHours(3 * 24 + 4)).ToInternalValue();
+  EXPECT_CALL(prefs, GetInt64(kPrefsInstallDateDays, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(0), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(future), Return(true)));
+  EXPECT_CALL(prefs, GetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(DoAll(SetArgumentPointee<1>(future), Return(true)));
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay, _))
+      .WillOnce(Return(true));
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay, _))
+      .WillOnce(Return(true));
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response "
+                      "protocol=\"3.0\"><daystart elapsed_seconds=\"100\"/>"
+                      "<app appid=\"foo\" status=\"ok\"><ping status=\"ok\"/>"
+                      "<updatecheck status=\"noupdate\"/></app></response>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_EQ(post_str.find("ping"), string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, LastPingDayUpdateTest) {
+  // This test checks that the action updates the last ping day to now
+  // minus 200 seconds with a slack of 5 seconds. Therefore, the test
+  // may fail if it runs for longer than 5 seconds. It shouldn't run
+  // that long though.
+  int64_t midnight =
+      (Time::Now() - TimeDelta::FromSeconds(200)).ToInternalValue();
+  int64_t midnight_slack =
+      (Time::Now() - TimeDelta::FromSeconds(195)).ToInternalValue();
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay,
+                              AllOf(Ge(midnight), Le(midnight_slack))))
+      .WillOnce(Return(true));
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay,
+                              AllOf(Ge(midnight), Le(midnight_slack))))
+      .WillOnce(Return(true));
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response "
+                      "protocol=\"3.0\"><daystart elapsed_seconds=\"200\"/>"
+                      "<app appid=\"foo\" status=\"ok\"><ping status=\"ok\"/>"
+                      "<updatecheck status=\"noupdate\"/></app></response>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      nullptr));
+}
+
+TEST_F(OmahaRequestActionTest, NoElapsedSecondsTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay, _)).Times(0);
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay, _)).Times(0);
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response "
+                      "protocol=\"3.0\"><daystart blah=\"200\"/>"
+                      "<app appid=\"foo\" status=\"ok\"><ping status=\"ok\"/>"
+                      "<updatecheck status=\"noupdate\"/></app></response>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      nullptr));
+}
+
+TEST_F(OmahaRequestActionTest, BadElapsedSecondsTest) {
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  EXPECT_CALL(prefs, GetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastActivePingDay, _)).Times(0);
+  EXPECT_CALL(prefs, SetInt64(kPrefsLastRollCallPingDay, _)).Times(0);
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "<?xml version=\"1.0\" encoding=\"UTF-8\"?><response "
+                      "protocol=\"3.0\"><daystart elapsed_seconds=\"x\"/>"
+                      "<app appid=\"foo\" status=\"ok\"><ping status=\"ok\"/>"
+                      "<updatecheck status=\"noupdate\"/></app></response>",
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      nullptr));
+}
+
+TEST_F(OmahaRequestActionTest, NoUniqueIDTest) {
+  brillo::Blob post_data;
+  ASSERT_FALSE(TestUpdateCheck(nullptr,  // request_params
+                               "invalid xml>",
+                               -1,
+                               false,  // ping_only
+                               ErrorCode::kOmahaRequestXMLParseError,
+                               metrics::CheckResult::kParsingError,
+                               metrics::CheckReaction::kUnset,
+                               metrics::DownloadErrorCode::kUnset,
+                               nullptr,  // response
+                               &post_data));
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_EQ(post_str.find("machineid="), string::npos);
+  EXPECT_EQ(post_str.find("userid="), string::npos);
+}
+
+TEST_F(OmahaRequestActionTest, NetworkFailureTest) {
+  OmahaResponse response;
+  const int http_error_code =
+      static_cast<int>(ErrorCode::kOmahaRequestHTTPResponseBase) + 501;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "",
+                      501,
+                      false,  // ping_only
+                      static_cast<ErrorCode>(http_error_code),
+                      metrics::CheckResult::kDownloadError,
+                      metrics::CheckReaction::kUnset,
+                      static_cast<metrics::DownloadErrorCode>(501),
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, NetworkFailureBadHTTPCodeTest) {
+  OmahaResponse response;
+  const int http_error_code =
+      static_cast<int>(ErrorCode::kOmahaRequestHTTPResponseBase) + 999;
+  ASSERT_FALSE(
+      TestUpdateCheck(nullptr,  // request_params
+                      "",
+                      1500,
+                      false,  // ping_only
+                      static_cast<ErrorCode>(http_error_code),
+                      metrics::CheckResult::kDownloadError,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kHttpStatusOther,
+                      &response,
+                      nullptr));
+  EXPECT_FALSE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, TestUpdateFirstSeenAtGetsPersistedFirstTime) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta().FromDays(1));
+  params.set_update_check_count_wait_enabled(false);
+
+  ASSERT_FALSE(TestUpdateCheck(
+                      &params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kOmahaUpdateDeferredPerPolicy,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kDeferring,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  int64_t timestamp = 0;
+  ASSERT_TRUE(fake_prefs_.GetInt64(kPrefsUpdateFirstSeenAt, &timestamp));
+  ASSERT_GT(timestamp, 0);
+  EXPECT_FALSE(response.update_exists);
+
+  // Verify if we are interactive check we don't defer.
+  params.set_interactive(true);
+  ASSERT_TRUE(
+      TestUpdateCheck(&params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+}
+
+TEST_F(OmahaRequestActionTest, TestUpdateFirstSeenAtGetsUsedIfAlreadyPresent) {
+  OmahaResponse response;
+  OmahaRequestParams params = request_params_;
+  params.set_wall_clock_based_wait_enabled(true);
+  params.set_waiting_period(TimeDelta().FromDays(1));
+  params.set_update_check_count_wait_enabled(false);
+
+  // Set the timestamp to a very old value such that it exceeds the
+  // waiting period set above.
+  Time t1;
+  Time::FromString("1/1/2012", &t1);
+  ASSERT_TRUE(fake_prefs_.SetInt64(
+      kPrefsUpdateFirstSeenAt, t1.ToInternalValue()));
+  ASSERT_TRUE(TestUpdateCheck(
+                      &params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+
+  EXPECT_TRUE(response.update_exists);
+
+  // Make sure the timestamp t1 is unchanged showing that it was reused.
+  int64_t timestamp = 0;
+  ASSERT_TRUE(fake_prefs_.GetInt64(kPrefsUpdateFirstSeenAt, &timestamp));
+  ASSERT_TRUE(timestamp == t1.ToInternalValue());
+}
+
+TEST_F(OmahaRequestActionTest, TestChangingToMoreStableChannel) {
+  // Create a uniquely named test directory.
+  string test_dir;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          "omaha_request_action-test-XXXXXX", &test_dir));
+
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir + "/etc"));
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir +
+                      kStatefulPartition + "/etc"));
+  brillo::Blob post_data;
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  ASSERT_TRUE(WriteFileString(
+      test_dir + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID={11111111-1111-1111-1111-111111111111}\n"
+      "CHROMEOS_BOARD_APPID={22222222-2222-2222-2222-222222222222}\n"
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_IS_POWERWASH_ALLOWED=true\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  OmahaRequestParams params = request_params_;
+  params.set_root(test_dir);
+  params.Init("1.2.3.4", "", 0);
+  EXPECT_EQ("canary-channel", params.current_channel());
+  EXPECT_EQ("stable-channel", params.target_channel());
+  EXPECT_TRUE(params.to_more_stable_channel());
+  EXPECT_TRUE(params.is_powerwash_allowed());
+  ASSERT_FALSE(TestUpdateCheck(&params,
+                               "invalid xml>",
+                               -1,
+                               false,  // ping_only
+                               ErrorCode::kOmahaRequestXMLParseError,
+                               metrics::CheckResult::kParsingError,
+                               metrics::CheckReaction::kUnset,
+                               metrics::DownloadErrorCode::kUnset,
+                               nullptr,  // response
+                               &post_data));
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(string::npos, post_str.find(
+      "appid=\"{22222222-2222-2222-2222-222222222222}\" "
+      "version=\"0.0.0.0\" from_version=\"1.2.3.4\" "
+      "track=\"stable-channel\" from_track=\"canary-channel\" "));
+
+  ASSERT_TRUE(base::DeleteFile(base::FilePath(test_dir), true));
+}
+
+TEST_F(OmahaRequestActionTest, TestChangingToLessStableChannel) {
+  // Create a uniquely named test directory.
+  string test_dir;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          "omaha_request_action-test-XXXXXX", &test_dir));
+
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir + "/etc"));
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir +
+                      kStatefulPartition + "/etc"));
+  brillo::Blob post_data;
+  NiceMock<MockPrefs> prefs;
+  fake_system_state_.set_prefs(&prefs);
+  ASSERT_TRUE(WriteFileString(
+      test_dir + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID={11111111-1111-1111-1111-111111111111}\n"
+      "CHROMEOS_BOARD_APPID={22222222-2222-2222-2222-222222222222}\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"));
+  OmahaRequestParams params = request_params_;
+  params.set_root(test_dir);
+  params.Init("5.6.7.8", "", 0);
+  EXPECT_EQ("stable-channel", params.current_channel());
+  EXPECT_EQ("canary-channel", params.target_channel());
+  EXPECT_FALSE(params.to_more_stable_channel());
+  EXPECT_FALSE(params.is_powerwash_allowed());
+  ASSERT_FALSE(TestUpdateCheck(&params,
+                               "invalid xml>",
+                               -1,
+                               false,  // ping_only
+                               ErrorCode::kOmahaRequestXMLParseError,
+                               metrics::CheckResult::kParsingError,
+                               metrics::CheckReaction::kUnset,
+                               metrics::DownloadErrorCode::kUnset,
+                               nullptr,  // response
+                               &post_data));
+  // convert post_data to string
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_NE(string::npos, post_str.find(
+      "appid=\"{11111111-1111-1111-1111-111111111111}\" "
+      "version=\"5.6.7.8\" "
+      "track=\"canary-channel\" from_track=\"stable-channel\""));
+  EXPECT_EQ(string::npos, post_str.find("from_version"));
+}
+
+// Checks that the initial ping with a=-1 r=-1 is not send when the device
+// was powerwashed.
+TEST_F(OmahaRequestActionTest, PingWhenPowerwashed) {
+  fake_prefs_.SetString(kPrefsPreviousVersion, "");
+
+  // Flag that the device was powerwashed in the past.
+  fake_system_state_.fake_hardware()->SetPowerwashCount(1);
+
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  // We shouldn't send a ping in this case since powerwash > 0.
+  string post_str(post_data.begin(), post_data.end());
+  EXPECT_EQ(string::npos, post_str.find("<ping"));
+}
+
+// Checks that the event 54 is sent on a reboot to a new update.
+TEST_F(OmahaRequestActionTest, RebootAfterUpdateEvent) {
+  // Flag that the device was updated in a previous boot.
+  fake_prefs_.SetString(kPrefsPreviousVersion, "1.2.3.4");
+
+  brillo::Blob post_data;
+  ASSERT_TRUE(
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetNoUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kNoUpdateAvailable,
+                      metrics::CheckReaction::kUnset,
+                      metrics::DownloadErrorCode::kUnset,
+                      nullptr,
+                      &post_data));
+  string post_str(post_data.begin(), post_data.end());
+
+  // An event 54 is included and has the right version.
+  EXPECT_NE(string::npos,
+            post_str.find(base::StringPrintf(
+                              "<event eventtype=\"%d\"",
+                              OmahaEvent::kTypeRebootedAfterUpdate)));
+  EXPECT_NE(string::npos,
+            post_str.find("previousversion=\"1.2.3.4\"></event>"));
+
+  // The previous version flag should have been removed.
+  EXPECT_TRUE(fake_prefs_.Exists(kPrefsPreviousVersion));
+  string prev_version;
+  EXPECT_TRUE(fake_prefs_.GetString(kPrefsPreviousVersion, &prev_version));
+  EXPECT_TRUE(prev_version.empty());
+}
+
+void OmahaRequestActionTest::P2PTest(
+    bool initial_allow_p2p_for_downloading,
+    bool initial_allow_p2p_for_sharing,
+    bool omaha_disable_p2p_for_downloading,
+    bool omaha_disable_p2p_for_sharing,
+    bool payload_state_allow_p2p_attempt,
+    bool expect_p2p_client_lookup,
+    const string& p2p_client_result_url,
+    bool expected_allow_p2p_for_downloading,
+    bool expected_allow_p2p_for_sharing,
+    const string& expected_p2p_url) {
+  OmahaResponse response;
+  OmahaRequestParams request_params = request_params_;
+  bool actual_allow_p2p_for_downloading = initial_allow_p2p_for_downloading;
+  bool actual_allow_p2p_for_sharing = initial_allow_p2p_for_sharing;
+  string actual_p2p_url;
+
+  MockPayloadState mock_payload_state;
+  fake_system_state_.set_payload_state(&mock_payload_state);
+  EXPECT_CALL(mock_payload_state, P2PAttemptAllowed())
+      .WillRepeatedly(Return(payload_state_allow_p2p_attempt));
+  EXPECT_CALL(mock_payload_state, GetUsingP2PForDownloading())
+      .WillRepeatedly(ReturnPointee(&actual_allow_p2p_for_downloading));
+  EXPECT_CALL(mock_payload_state, GetUsingP2PForSharing())
+      .WillRepeatedly(ReturnPointee(&actual_allow_p2p_for_sharing));
+  EXPECT_CALL(mock_payload_state, SetUsingP2PForDownloading(_))
+      .WillRepeatedly(SaveArg<0>(&actual_allow_p2p_for_downloading));
+  EXPECT_CALL(mock_payload_state, SetUsingP2PForSharing(_))
+      .WillRepeatedly(SaveArg<0>(&actual_allow_p2p_for_sharing));
+  EXPECT_CALL(mock_payload_state, SetP2PUrl(_))
+      .WillRepeatedly(SaveArg<0>(&actual_p2p_url));
+
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetLookupUrlForFileResult(p2p_client_result_url);
+
+  TimeDelta timeout = TimeDelta::FromSeconds(kMaxP2PNetworkWaitTimeSeconds);
+  EXPECT_CALL(mock_p2p_manager, LookupUrlForFile(_, _, timeout, _))
+      .Times(expect_p2p_client_lookup ? 1 : 0);
+
+  fake_update_response_.disable_p2p_for_downloading =
+      omaha_disable_p2p_for_downloading;
+  fake_update_response_.disable_p2p_for_sharing = omaha_disable_p2p_for_sharing;
+  ASSERT_TRUE(
+      TestUpdateCheck(&request_params,
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      &response,
+                      nullptr));
+  EXPECT_TRUE(response.update_exists);
+
+  EXPECT_EQ(omaha_disable_p2p_for_downloading,
+            response.disable_p2p_for_downloading);
+  EXPECT_EQ(omaha_disable_p2p_for_sharing,
+            response.disable_p2p_for_sharing);
+
+  EXPECT_EQ(expected_allow_p2p_for_downloading,
+            actual_allow_p2p_for_downloading);
+  EXPECT_EQ(expected_allow_p2p_for_sharing, actual_allow_p2p_for_sharing);
+  EXPECT_EQ(expected_p2p_url, actual_p2p_url);
+}
+
+TEST_F(OmahaRequestActionTest, P2PWithPeer) {
+  P2PTest(true,                   // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          false,                  // omaha_disable_p2p_for_downloading
+          false,                  // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          true,                   // expect_p2p_client_lookup
+          "http://1.3.5.7/p2p",   // p2p_client_result_url
+          true,                   // expected_allow_p2p_for_downloading
+          true,                   // expected_allow_p2p_for_sharing
+          "http://1.3.5.7/p2p");  // expected_p2p_url
+}
+
+TEST_F(OmahaRequestActionTest, P2PWithoutPeer) {
+  P2PTest(true,                   // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          false,                  // omaha_disable_p2p_for_downloading
+          false,                  // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          true,                   // expect_p2p_client_lookup
+          "",                     // p2p_client_result_url
+          false,                  // expected_allow_p2p_for_downloading
+          true,                   // expected_allow_p2p_for_sharing
+          "");                    // expected_p2p_url
+}
+
+TEST_F(OmahaRequestActionTest, P2PDownloadNotAllowed) {
+  P2PTest(false,                  // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          false,                  // omaha_disable_p2p_for_downloading
+          false,                  // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          false,                  // expect_p2p_client_lookup
+          "unset",                // p2p_client_result_url
+          false,                  // expected_allow_p2p_for_downloading
+          true,                   // expected_allow_p2p_for_sharing
+          "");                    // expected_p2p_url
+}
+
+TEST_F(OmahaRequestActionTest, P2PWithPeerDownloadDisabledByOmaha) {
+  P2PTest(true,                   // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          true,                   // omaha_disable_p2p_for_downloading
+          false,                  // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          false,                  // expect_p2p_client_lookup
+          "unset",                // p2p_client_result_url
+          false,                  // expected_allow_p2p_for_downloading
+          true,                   // expected_allow_p2p_for_sharing
+          "");                    // expected_p2p_url
+}
+
+TEST_F(OmahaRequestActionTest, P2PWithPeerSharingDisabledByOmaha) {
+  P2PTest(true,                   // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          false,                  // omaha_disable_p2p_for_downloading
+          true,                   // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          true,                   // expect_p2p_client_lookup
+          "http://1.3.5.7/p2p",   // p2p_client_result_url
+          true,                   // expected_allow_p2p_for_downloading
+          false,                  // expected_allow_p2p_for_sharing
+          "http://1.3.5.7/p2p");  // expected_p2p_url
+}
+
+TEST_F(OmahaRequestActionTest, P2PWithPeerBothDisabledByOmaha) {
+  P2PTest(true,                   // initial_allow_p2p_for_downloading
+          true,                   // initial_allow_p2p_for_sharing
+          true,                   // omaha_disable_p2p_for_downloading
+          true,                   // omaha_disable_p2p_for_sharing
+          true,                   // payload_state_allow_p2p_attempt
+          false,                  // expect_p2p_client_lookup
+          "unset",                // p2p_client_result_url
+          false,                  // expected_allow_p2p_for_downloading
+          false,                  // expected_allow_p2p_for_sharing
+          "");                    // expected_p2p_url
+}
+
+bool OmahaRequestActionTest::InstallDateParseHelper(const string &elapsed_days,
+                                                    OmahaResponse *response) {
+  fake_update_response_.elapsed_days = elapsed_days;
+  return
+      TestUpdateCheck(nullptr,  // request_params
+                      fake_update_response_.GetUpdateResponse(),
+                      -1,
+                      false,  // ping_only
+                      ErrorCode::kSuccess,
+                      metrics::CheckResult::kUpdateAvailable,
+                      metrics::CheckReaction::kUpdating,
+                      metrics::DownloadErrorCode::kUnset,
+                      response,
+                      nullptr);
+}
+
+TEST_F(OmahaRequestActionTest, ParseInstallDateFromResponse) {
+  OmahaResponse response;
+
+  // Check that we parse elapsed_days in the Omaha Response correctly.
+  // and that the kPrefsInstallDateDays value is written to.
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsInstallDateDays));
+  EXPECT_TRUE(InstallDateParseHelper("42", &response));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ(42, response.install_date_days);
+  EXPECT_TRUE(fake_prefs_.Exists(kPrefsInstallDateDays));
+  int64_t prefs_days;
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 42);
+
+  // If there already is a value set, we shouldn't do anything.
+  EXPECT_TRUE(InstallDateParseHelper("7", &response));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ(7, response.install_date_days);
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 42);
+
+  // Note that elapsed_days is not necessarily divisible by 7 so check
+  // that we round down correctly when populating kPrefsInstallDateDays.
+  EXPECT_TRUE(fake_prefs_.Delete(kPrefsInstallDateDays));
+  EXPECT_TRUE(InstallDateParseHelper("23", &response));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ(23, response.install_date_days);
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 21);
+
+  // Check that we correctly handle elapsed_days not being included in
+  // the Omaha Response.
+  EXPECT_TRUE(InstallDateParseHelper("", &response));
+  EXPECT_TRUE(response.update_exists);
+  EXPECT_EQ(-1, response.install_date_days);
+}
+
+// If there is no prefs and OOBE is not complete, we should not
+// report anything to Omaha.
+TEST_F(OmahaRequestActionTest, GetInstallDateWhenNoPrefsNorOOBE) {
+  EXPECT_EQ(OmahaRequestAction::GetInstallDate(&fake_system_state_), -1);
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsInstallDateDays));
+}
+
+// If OOBE is complete and happened on a valid date (e.g. after Jan
+// 1 2007 0:00 PST), that date should be used and written to
+// prefs. However, first try with an invalid date and check we do
+// nothing.
+TEST_F(OmahaRequestActionTest, GetInstallDateWhenOOBECompletedWithInvalidDate) {
+  Time oobe_date = Time::FromTimeT(42);  // Dec 31, 1969 16:00:42 PST.
+  fake_system_state_.fake_hardware()->SetIsOOBEComplete(oobe_date);
+  EXPECT_EQ(OmahaRequestAction::GetInstallDate(&fake_system_state_), -1);
+  EXPECT_FALSE(fake_prefs_.Exists(kPrefsInstallDateDays));
+}
+
+// Then check with a valid date. The date Jan 20, 2007 0:00 PST
+// should yield an InstallDate of 14.
+TEST_F(OmahaRequestActionTest, GetInstallDateWhenOOBECompletedWithValidDate) {
+  Time oobe_date = Time::FromTimeT(1169280000);  // Jan 20, 2007 0:00 PST.
+  fake_system_state_.fake_hardware()->SetIsOOBEComplete(oobe_date);
+  EXPECT_EQ(OmahaRequestAction::GetInstallDate(&fake_system_state_), 14);
+  EXPECT_TRUE(fake_prefs_.Exists(kPrefsInstallDateDays));
+
+  int64_t prefs_days;
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 14);
+}
+
+// Now that we have a valid date in prefs, check that we keep using
+// that even if OOBE date reports something else. The date Jan 30,
+// 2007 0:00 PST should yield an InstallDate of 28... but since
+// there's a prefs file, we should still get 14.
+TEST_F(OmahaRequestActionTest, GetInstallDateWhenOOBECompletedDateChanges) {
+  // Set a valid date in the prefs first.
+  EXPECT_TRUE(fake_prefs_.SetInt64(kPrefsInstallDateDays, 14));
+
+  Time oobe_date = Time::FromTimeT(1170144000);  // Jan 30, 2007 0:00 PST.
+  fake_system_state_.fake_hardware()->SetIsOOBEComplete(oobe_date);
+  EXPECT_EQ(OmahaRequestAction::GetInstallDate(&fake_system_state_), 14);
+
+  int64_t prefs_days;
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 14);
+
+  // If we delete the prefs file, we should get 28 days.
+  EXPECT_TRUE(fake_prefs_.Delete(kPrefsInstallDateDays));
+  EXPECT_EQ(OmahaRequestAction::GetInstallDate(&fake_system_state_), 28);
+  EXPECT_TRUE(fake_prefs_.GetInt64(kPrefsInstallDateDays, &prefs_days));
+  EXPECT_EQ(prefs_days, 28);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/omaha_request_params.cc b/omaha_request_params.cc
new file mode 100644
index 0000000..d0011f7
--- /dev/null
+++ b/omaha_request_params.cc
@@ -0,0 +1,215 @@
+//
+// Copyright (C) 2011 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 "update_engine/omaha_request_params.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <sys/utsname.h>
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/key_value_store.h>
+#include <brillo/strings/string_utils.h>
+#include <policy/device_policy.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/system_state.h"
+
+#define CALL_MEMBER_FN(object, member) ((object).*(member))
+
+using std::map;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+const char OmahaRequestParams::kOsVersion[] = "Indy";
+
+const char* kChannelsByStability[] = {
+    // This list has to be sorted from least stable to most stable channel.
+    "canary-channel",
+    "dev-channel",
+    "beta-channel",
+    "stable-channel",
+};
+
+OmahaRequestParams::~OmahaRequestParams() {
+  if (!root_.empty())
+    test::SetImagePropertiesRootPrefix(nullptr);
+}
+
+bool OmahaRequestParams::Init(const string& in_app_version,
+                              const string& in_update_url,
+                              bool in_interactive) {
+  LOG(INFO) << "Initializing parameters for this update attempt";
+  image_props_ = LoadImageProperties(system_state_);
+  mutable_image_props_ = LoadMutableImageProperties(system_state_);
+
+  // Sanity check the channel names.
+  if (!IsValidChannel(image_props_.current_channel))
+    image_props_.current_channel = "stable-channel";
+  if (!IsValidChannel(mutable_image_props_.target_channel))
+    mutable_image_props_.target_channel = image_props_.current_channel;
+  UpdateDownloadChannel();
+
+  LOG(INFO) << "Running from channel " << image_props_.current_channel;
+
+  os_platform_ = constants::kOmahaPlatformName;
+  os_version_ = OmahaRequestParams::kOsVersion;
+  if (!in_app_version.empty())
+    image_props_.version = in_app_version;
+
+  os_sp_ = image_props_.version + "_" + GetMachineType();
+  app_lang_ = "en-US";
+  hwid_ = system_state_->hardware()->GetHardwareClass();
+  if (CollectECFWVersions()) {
+    fw_version_ = system_state_->hardware()->GetFirmwareVersion();
+    ec_version_ = system_state_->hardware()->GetECVersion();
+  }
+
+  if (image_props_.current_channel == mutable_image_props_.target_channel) {
+    // deltas are only okay if the /.nodelta file does not exist.  if we don't
+    // know (i.e. stat() returns some unexpected error), then err on the side of
+    // caution and say deltas are not okay.
+    struct stat stbuf;
+    delta_okay_ = (stat((root_ + "/.nodelta").c_str(), &stbuf) < 0) &&
+                  (errno == ENOENT);
+  } else {
+    LOG(INFO) << "Disabling deltas as a channel change to "
+              << mutable_image_props_.target_channel
+              << " is pending, with is_powerwash_allowed="
+              << utils::ToString(mutable_image_props_.is_powerwash_allowed);
+    // For now, disable delta updates if the current channel is different from
+    // the channel that we're sending to the update server because such updates
+    // are destined to fail -- the current rootfs hash will be different than
+    // the expected hash due to the different channel in /etc/lsb-release.
+    delta_okay_ = false;
+  }
+
+  if (in_update_url.empty())
+    update_url_ = image_props_.omaha_url;
+  else
+    update_url_ = in_update_url;
+
+  // Set the interactive flag accordingly.
+  interactive_ = in_interactive;
+  return true;
+}
+
+bool OmahaRequestParams::IsUpdateUrlOfficial() const {
+  return (update_url_ == constants::kOmahaDefaultAUTestURL ||
+          update_url_ == image_props_.omaha_url);
+}
+
+bool OmahaRequestParams::CollectECFWVersions() const {
+  return base::StartsWithASCII(hwid_, string("SAMS ALEX"), true) ||
+         base::StartsWithASCII(hwid_, string("BUTTERFLY"), true) ||
+         base::StartsWithASCII(hwid_, string("LUMPY"), true) ||
+         base::StartsWithASCII(hwid_, string("PARROT"), true) ||
+         base::StartsWithASCII(hwid_, string("SPRING"), true) ||
+         base::StartsWithASCII(hwid_, string("SNOW"), true);
+}
+
+bool OmahaRequestParams::SetTargetChannel(const string& new_target_channel,
+                                          bool is_powerwash_allowed,
+                                          string* error_message) {
+  LOG(INFO) << "SetTargetChannel called with " << new_target_channel
+            << ", Is Powerwash Allowed = "
+            << utils::ToString(is_powerwash_allowed)
+            << ". Current channel = " << image_props_.current_channel
+            << ", existing target channel = "
+            << mutable_image_props_.target_channel
+            << ", download channel = " << download_channel_;
+  if (!IsValidChannel(new_target_channel)) {
+    string valid_channels = brillo::string_utils::JoinRange(
+        ", ",
+        std::begin(kChannelsByStability),
+        std::end(kChannelsByStability));
+    if (error_message) {
+      *error_message = base::StringPrintf(
+          "Invalid channel name \"%s\", valid names are: %s",
+          new_target_channel.c_str(), valid_channels.c_str());
+    }
+    return false;
+  }
+
+  MutableImageProperties new_props;
+  new_props.target_channel = new_target_channel;
+  new_props.is_powerwash_allowed = is_powerwash_allowed;
+
+  if (!StoreMutableImageProperties(system_state_, new_props)) {
+    if (error_message)
+      *error_message = "Error storing the new channel value.";
+    return false;
+  }
+  mutable_image_props_ = new_props;
+  return true;
+}
+
+void OmahaRequestParams::UpdateDownloadChannel() {
+  if (download_channel_ != mutable_image_props_.target_channel) {
+    download_channel_ = mutable_image_props_.target_channel;
+    LOG(INFO) << "Download channel for this attempt = " << download_channel_;
+  }
+}
+
+string OmahaRequestParams::GetMachineType() const {
+  struct utsname buf;
+  string ret;
+  if (uname(&buf) == 0)
+    ret = buf.machine;
+  return ret;
+}
+
+bool OmahaRequestParams::IsValidChannel(const string& channel) const {
+  return GetChannelIndex(channel) >= 0;
+}
+
+void OmahaRequestParams::set_root(const string& root) {
+  root_ = root;
+  test::SetImagePropertiesRootPrefix(root_.c_str());
+}
+
+int OmahaRequestParams::GetChannelIndex(const string& channel) const {
+  for (size_t t = 0; t < arraysize(kChannelsByStability); ++t)
+    if (channel == kChannelsByStability[t])
+      return t;
+
+  return -1;
+}
+
+bool OmahaRequestParams::to_more_stable_channel() const {
+  int current_channel_index = GetChannelIndex(image_props_.current_channel);
+  int download_channel_index = GetChannelIndex(download_channel_);
+
+  return download_channel_index > current_channel_index;
+}
+
+string OmahaRequestParams::GetAppId() const {
+  return download_channel_ == "canary-channel" ? image_props_.canary_product_id
+                                               : image_props_.product_id;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/omaha_request_params.h b/omaha_request_params.h
new file mode 100644
index 0000000..b4534a1
--- /dev/null
+++ b/omaha_request_params.h
@@ -0,0 +1,336 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_OMAHA_REQUEST_PARAMS_H_
+#define UPDATE_ENGINE_OMAHA_REQUEST_PARAMS_H_
+
+#include <stdint.h>
+
+#include <string>
+
+#include <base/macros.h>
+#include <base/time/time.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/image_properties.h"
+
+// This gathers local system information and prepares info used by the
+// Omaha request action.
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+// This class encapsulates the data Omaha gets for the request, along with
+// essential state needed for the processing of the request/response.  The
+// strings in this struct should not be XML escaped.
+//
+// TODO(jaysri): chromium-os:39752 tracks the need to rename this class to
+// reflect its lifetime more appropriately.
+class OmahaRequestParams {
+ public:
+  explicit OmahaRequestParams(SystemState* system_state)
+      : system_state_(system_state),
+        os_platform_(constants::kOmahaPlatformName),
+        os_version_(kOsVersion),
+        delta_okay_(true),
+        interactive_(false),
+        wall_clock_based_wait_enabled_(false),
+        update_check_count_wait_enabled_(false),
+        min_update_checks_needed_(kDefaultMinUpdateChecks),
+        max_update_checks_allowed_(kDefaultMaxUpdateChecks) {}
+
+  OmahaRequestParams(SystemState* system_state,
+                     const std::string& in_os_platform,
+                     const std::string& in_os_version,
+                     const std::string& in_os_sp,
+                     const std::string& in_os_board,
+                     const std::string& in_app_id,
+                     const std::string& in_app_version,
+                     const std::string& in_app_lang,
+                     const std::string& in_target_channel,
+                     const std::string& in_hwid,
+                     const std::string& in_fw_version,
+                     const std::string& in_ec_version,
+                     bool in_delta_okay,
+                     bool in_interactive,
+                     const std::string& in_update_url,
+                     const std::string& in_target_version_prefix)
+      : system_state_(system_state),
+        os_platform_(in_os_platform),
+        os_version_(in_os_version),
+        os_sp_(in_os_sp),
+        app_lang_(in_app_lang),
+        hwid_(in_hwid),
+        fw_version_(in_fw_version),
+        ec_version_(in_ec_version),
+        delta_okay_(in_delta_okay),
+        interactive_(in_interactive),
+        update_url_(in_update_url),
+        target_version_prefix_(in_target_version_prefix),
+        wall_clock_based_wait_enabled_(false),
+        update_check_count_wait_enabled_(false),
+        min_update_checks_needed_(kDefaultMinUpdateChecks),
+        max_update_checks_allowed_(kDefaultMaxUpdateChecks) {
+    image_props_.board = in_os_board;
+    image_props_.product_id = in_app_id;
+    image_props_.canary_product_id = in_app_id;
+    image_props_.version = in_app_version;
+    image_props_.current_channel = in_target_channel;
+    mutable_image_props_.target_channel = in_target_channel;
+    mutable_image_props_.is_powerwash_allowed = false;
+  }
+
+  virtual ~OmahaRequestParams();
+
+  // Setters and getters for the various properties.
+  inline std::string os_platform() const { return os_platform_; }
+  inline std::string os_version() const { return os_version_; }
+  inline std::string os_sp() const { return os_sp_; }
+  inline std::string os_board() const { return image_props_.board; }
+  inline std::string board_app_id() const { return image_props_.product_id; }
+  inline std::string canary_app_id() const {
+    return image_props_.canary_product_id;
+  }
+  inline std::string app_lang() const { return app_lang_; }
+  inline std::string hwid() const { return hwid_; }
+  inline std::string fw_version() const { return fw_version_; }
+  inline std::string ec_version() const { return ec_version_; }
+
+  inline void set_app_version(const std::string& version) {
+    image_props_.version = version;
+  }
+  inline std::string app_version() const { return image_props_.version; }
+
+  inline std::string current_channel() const {
+    return image_props_.current_channel;
+  }
+  inline std::string target_channel() const {
+    return mutable_image_props_.target_channel;
+  }
+  inline std::string download_channel() const { return download_channel_; }
+
+  // Can client accept a delta ?
+  inline void set_delta_okay(bool ok) { delta_okay_ = ok; }
+  inline bool delta_okay() const { return delta_okay_; }
+
+  // True if this is a user-initiated update check.
+  inline void set_interactive(bool interactive) { interactive_ = interactive; }
+  inline bool interactive() const { return interactive_; }
+
+  inline void set_update_url(const std::string& url) { update_url_ = url; }
+  inline std::string update_url() const { return update_url_; }
+
+  inline void set_target_version_prefix(const std::string& prefix) {
+    target_version_prefix_ = prefix;
+  }
+
+  inline std::string target_version_prefix() const {
+    return target_version_prefix_;
+  }
+
+  inline void set_wall_clock_based_wait_enabled(bool enabled) {
+    wall_clock_based_wait_enabled_ = enabled;
+  }
+  inline bool wall_clock_based_wait_enabled() const {
+    return wall_clock_based_wait_enabled_;
+  }
+
+  inline void set_waiting_period(base::TimeDelta period) {
+    waiting_period_ = period;
+  }
+  base::TimeDelta waiting_period() const { return waiting_period_; }
+
+  inline void set_update_check_count_wait_enabled(bool enabled) {
+    update_check_count_wait_enabled_ = enabled;
+  }
+
+  inline bool update_check_count_wait_enabled() const {
+    return update_check_count_wait_enabled_;
+  }
+
+  inline void set_min_update_checks_needed(int64_t min) {
+    min_update_checks_needed_ = min;
+  }
+  inline int64_t min_update_checks_needed() const {
+    return min_update_checks_needed_;
+  }
+
+  inline void set_max_update_checks_allowed(int64_t max) {
+    max_update_checks_allowed_ = max;
+  }
+  inline int64_t max_update_checks_allowed() const {
+    return max_update_checks_allowed_;
+  }
+
+  // True if we're trying to update to a more stable channel.
+  // i.e. index(target_channel) > index(current_channel).
+  virtual bool to_more_stable_channel() const;
+
+  // Returns the app id corresponding to the current value of the
+  // download channel.
+  virtual std::string GetAppId() const;
+
+  // Suggested defaults
+  static const char kOsVersion[];
+  static const char kIsPowerwashAllowedKey[];
+  static const int64_t kDefaultMinUpdateChecks = 0;
+  static const int64_t kDefaultMaxUpdateChecks = 8;
+
+  // Initializes all the data in the object. Non-empty
+  // |in_app_version| or |in_update_url| prevents automatic detection
+  // of the parameter. Returns true on success, false otherwise.
+  bool Init(const std::string& in_app_version,
+            const std::string& in_update_url,
+            bool in_interactive);
+
+  // Permanently changes the release channel to |channel|. Performs a
+  // powerwash, if required and allowed.
+  // Returns true on success, false otherwise. Note: This call will fail if
+  // there's a channel change pending already. This is to serialize all the
+  // channel changes done by the user in order to avoid having to solve
+  // numerous edge cases around ensuring the powerwash happens as intended in
+  // all such cases.
+  virtual bool SetTargetChannel(const std::string& channel,
+                                bool is_powerwash_allowed,
+                                std::string* error_message);
+
+  // Updates the download channel for this particular attempt from the current
+  // value of target channel.  This method takes a "snapshot" of the current
+  // value of target channel and uses it for all subsequent Omaha requests for
+  // this attempt (i.e. initial request as well as download progress/error
+  // event requests). The snapshot will be updated only when either this method
+  // or Init is called again.
+  virtual void UpdateDownloadChannel();
+
+  virtual bool is_powerwash_allowed() const {
+    return mutable_image_props_.is_powerwash_allowed;
+  }
+
+  // Check if the provided update URL is official, meaning either the default
+  // autoupdate server or the autoupdate autotest server.
+  virtual bool IsUpdateUrlOfficial() const;
+
+  // For unit-tests.
+  void set_root(const std::string& root);
+  void set_current_channel(const std::string& channel) {
+    image_props_.current_channel = channel;
+  }
+  void set_target_channel(const std::string& channel) {
+    mutable_image_props_.target_channel = channel;
+  }
+
+ private:
+  FRIEND_TEST(OmahaRequestParamsTest, IsValidChannelTest);
+  FRIEND_TEST(OmahaRequestParamsTest, ShouldLockDownTest);
+  FRIEND_TEST(OmahaRequestParamsTest, ChannelIndexTest);
+  FRIEND_TEST(OmahaRequestParamsTest, LsbPreserveTest);
+  FRIEND_TEST(OmahaRequestParamsTest, CollectECFWVersionsTest);
+
+  // Returns true if |channel| is a valid channel, false otherwise.
+  bool IsValidChannel(const std::string& channel) const;
+
+  // Returns the index of the given channel.
+  int GetChannelIndex(const std::string& channel) const;
+
+  // Returns True if we should store the fw/ec versions based on our hwid_.
+  // Compares hwid to a set of whitelisted prefixes.
+  bool CollectECFWVersions() const;
+
+  // These are individual helper methods to initialize the said properties from
+  // the LSB value.
+  void SetTargetChannelFromLsbValue();
+  void SetCurrentChannelFromLsbValue();
+  void SetIsPowerwashAllowedFromLsbValue();
+
+  // Initializes the required properties from the LSB value.
+  void InitFromLsbValue();
+
+  // Gets the machine type (e.g. "i686").
+  std::string GetMachineType() const;
+
+  // Global system context.
+  SystemState* system_state_;
+
+  // The system image properties.
+  ImageProperties image_props_;
+  MutableImageProperties mutable_image_props_;
+
+  // Basic properties of the OS and Application that go into the Omaha request.
+  std::string os_platform_;
+  std::string os_version_;
+  std::string os_sp_;
+  std::string app_lang_;
+
+  // There are three channel values we deal with:
+  // * The channel we got the image we are running from or "current channel"
+  //   stored in |image_props_.current_channel|.
+  //
+  // * The release channel we are tracking, where we should get updates from,
+  //   stored in |mutable_image_props_.target_channel|. This channel is
+  //   normally the same as the current_channel, except when the user changes
+  //   the channel. In that case it'll have the release channel the user
+  //   switched to, regardless of whether we downloaded an update from that
+  //   channel or not, or if we are in the middle of a download from a
+  //   previously selected channel  (as opposed to download channel
+  //   which gets updated only at the start of next download).
+  //
+  // * The channel from which we're downloading the payload. This should
+  //   normally be the same as target channel. But if the user made another
+  //   channel change after we started the download, then they'd be different,
+  //   in which case, we'd detect elsewhere that the target channel has been
+  //   changed and cancel the current download attempt.
+  std::string download_channel_;
+
+  std::string hwid_;  // Hardware Qualification ID of the client
+  std::string fw_version_;  // Chrome OS Firmware Version.
+  std::string ec_version_;  // Chrome OS EC Version.
+  bool delta_okay_;  // If this client can accept a delta
+  bool interactive_;   // Whether this is a user-initiated update check
+
+  // The URL to send the Omaha request to.
+  std::string update_url_;
+
+  // Prefix of the target OS version that the enterprise wants this device
+  // to be pinned to. It's empty otherwise.
+  std::string target_version_prefix_;
+
+  // True if scattering is enabled, in which case waiting_period_ specifies the
+  // amount of absolute time that we've to wait for before sending a request to
+  // Omaha.
+  bool wall_clock_based_wait_enabled_;
+  base::TimeDelta waiting_period_;
+
+  // True if scattering is enabled to denote the number of update checks
+  // we've to skip before we can send a request to Omaha. The min and max
+  // values establish the bounds for a random number to be chosen within that
+  // range to enable such a wait.
+  bool update_check_count_wait_enabled_;
+  int64_t min_update_checks_needed_;
+  int64_t max_update_checks_allowed_;
+
+  // When reading files, prepend root_ to the paths. Useful for testing.
+  std::string root_;
+
+  // TODO(jaysri): Uncomment this after fixing unit tests, as part of
+  // chromium-os:39752
+  // DISALLOW_COPY_AND_ASSIGN(OmahaRequestParams);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_OMAHA_REQUEST_PARAMS_H_
diff --git a/omaha_request_params_unittest.cc b/omaha_request_params_unittest.cc
new file mode 100644
index 0000000..33dd6d5
--- /dev/null
+++ b/omaha_request_params_unittest.cc
@@ -0,0 +1,598 @@
+//
+// Copyright (C) 2011 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 "update_engine/omaha_request_params.h"
+
+#include <stdio.h>
+
+#include <string>
+
+#include <base/files/file_util.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/payload_consumer/install_plan.h"
+
+using chromeos_update_engine::test_utils::WriteFileString;
+using std::string;
+
+namespace chromeos_update_engine {
+
+class OmahaRequestParamsTest : public ::testing::Test {
+ public:
+  OmahaRequestParamsTest() : params_(&fake_system_state_) {}
+
+ protected:
+  // Return true iff the OmahaRequestParams::Init succeeded. If
+  // out is non-null, it's set w/ the generated data.
+  bool DoTest(OmahaRequestParams* out, const string& app_version,
+              const string& omaha_url);
+
+  void SetUp() override {
+    // Create a uniquely named test directory.
+    ASSERT_TRUE(utils::MakeTempDirectory(kTestDirTemplate, &test_dir_));
+    EXPECT_TRUE(base::CreateDirectory(base::FilePath(test_dir_ + "/etc")));
+    EXPECT_TRUE(base::CreateDirectory(
+        base::FilePath(test_dir_ + kStatefulPartition + "/etc")));
+    // Create a fresh copy of the params for each test, so there's no
+    // unintended reuse of state across tests.
+    OmahaRequestParams new_params(&fake_system_state_);
+    params_ = new_params;
+    params_.set_root(test_dir_);
+    SetLockDown(false);
+  }
+
+  void TearDown() override {
+    EXPECT_TRUE(base::DeleteFile(base::FilePath(test_dir_), true));
+  }
+
+  void SetLockDown(bool locked_down) {
+    fake_system_state_.fake_hardware()->SetIsOfficialBuild(locked_down);
+    fake_system_state_.fake_hardware()->SetIsNormalBootMode(locked_down);
+  }
+
+  OmahaRequestParams params_;
+  FakeSystemState fake_system_state_;
+
+  static const char* kTestDirTemplate;
+  string test_dir_;
+};
+
+const char* OmahaRequestParamsTest::kTestDirTemplate =
+  "omaha_request_params-test-XXXXXX";
+
+bool OmahaRequestParamsTest::DoTest(OmahaRequestParams* out,
+                                    const string& app_version,
+                                    const string& omaha_url) {
+  bool success = params_.Init(app_version, omaha_url, false);
+  if (out)
+    *out = params_;
+  return success;
+}
+
+namespace {
+string GetMachineType() {
+  string machine_type;
+  if (!utils::ReadPipe("uname -m", &machine_type))
+    return "";
+  // Strip anything from the first newline char.
+  size_t newline_pos = machine_type.find('\n');
+  if (newline_pos != string::npos)
+    machine_type.erase(newline_pos);
+  return machine_type;
+}
+}  // namespace
+
+TEST_F(OmahaRequestParamsTest, SimpleTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ("http://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, AppIDTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_RELEASE_APPID={58c35cef-9d30-476e-9098-ce20377d535d}\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{58c35cef-9d30-476e-9098-ce20377d535d}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ("http://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, MissingChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRXCK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  // By default, if no channel is set, we should track the stable-channel.
+  EXPECT_EQ("stable-channel", out.target_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, ConfusingReleaseTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_FOO=CHROMEOS_RELEASE_VERSION=1.2.3.4\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRXCK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_EQ("stable-channel", out.target_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, MissingVersionTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, ForceVersionTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "ForcedVersion", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("ForcedVersion_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("ForcedVersion", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, ForcedURLTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", "http://forced.google.com"));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ("http://forced.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, MissingURLTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ(constants::kOmahaDefaultProductionURL, out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, NoDeltasTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_FOO=CHROMEOS_RELEASE_VERSION=1.2.3.4\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRXCK=dev-channel"));
+  ASSERT_TRUE(WriteFileString(test_dir_ + "/.nodelta", ""));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_FALSE(out.delta_okay());
+}
+
+TEST_F(OmahaRequestParamsTest, OverrideTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=x86-generic\n"
+      "CHROMEOS_RELEASE_TRACK=beta-channel\n"
+      "CHROMEOS_AUSERVER=https://www.google.com"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("x86-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_FALSE(out.delta_okay());
+  EXPECT_EQ("beta-channel", out.target_channel());
+  EXPECT_EQ("https://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, OverrideLockDownTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=https://www.google.com"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=x86-generic\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  SetLockDown(true);
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_FALSE(out.delta_okay());
+  EXPECT_EQ("stable-channel", out.target_channel());
+  EXPECT_EQ("https://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, OverrideSameChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=x86-generic\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("x86-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ("http://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, SetTargetChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  {
+    OmahaRequestParams params(&fake_system_state_);
+    params.set_root(test_dir_);
+    EXPECT_TRUE(params.Init("", "", false));
+    params.SetTargetChannel("canary-channel", false, nullptr);
+    EXPECT_FALSE(params.is_powerwash_allowed());
+  }
+  OmahaRequestParams out(&fake_system_state_);
+  out.set_root(test_dir_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("canary-channel", out.target_channel());
+  EXPECT_FALSE(out.is_powerwash_allowed());
+}
+
+TEST_F(OmahaRequestParamsTest, SetIsPowerwashAllowedTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  {
+    OmahaRequestParams params(&fake_system_state_);
+    params.set_root(test_dir_);
+    EXPECT_TRUE(params.Init("", "", false));
+    params.SetTargetChannel("canary-channel", true, nullptr);
+    EXPECT_TRUE(params.is_powerwash_allowed());
+  }
+  OmahaRequestParams out(&fake_system_state_);
+  out.set_root(test_dir_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("canary-channel", out.target_channel());
+  EXPECT_TRUE(out.is_powerwash_allowed());
+}
+
+TEST_F(OmahaRequestParamsTest, SetTargetChannelInvalidTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  {
+    OmahaRequestParams params(&fake_system_state_);
+    params.set_root(test_dir_);
+    SetLockDown(true);
+    EXPECT_TRUE(params.Init("", "", false));
+    string error_message;
+    EXPECT_FALSE(
+        params.SetTargetChannel("dogfood-channel", true, &error_message));
+    // The error message should include a message about the valid channels.
+    EXPECT_NE(string::npos, error_message.find("stable-channel"));
+    EXPECT_FALSE(params.is_powerwash_allowed());
+  }
+  OmahaRequestParams out(&fake_system_state_);
+  out.set_root(test_dir_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_FALSE(out.is_powerwash_allowed());
+}
+
+TEST_F(OmahaRequestParamsTest, IsValidChannelTest) {
+  EXPECT_TRUE(params_.IsValidChannel("canary-channel"));
+  EXPECT_TRUE(params_.IsValidChannel("stable-channel"));
+  EXPECT_TRUE(params_.IsValidChannel("beta-channel"));
+  EXPECT_TRUE(params_.IsValidChannel("dev-channel"));
+  EXPECT_FALSE(params_.IsValidChannel("testimage-channel"));
+  EXPECT_FALSE(params_.IsValidChannel("dogfood-channel"));
+  EXPECT_FALSE(params_.IsValidChannel("some-channel"));
+  EXPECT_FALSE(params_.IsValidChannel(""));
+}
+
+TEST_F(OmahaRequestParamsTest, ValidChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  SetLockDown(true);
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("Chrome OS", out.os_platform());
+  EXPECT_EQ(string("0.2.2.3_") + GetMachineType(), out.os_sp());
+  EXPECT_EQ("arm-generic", out.os_board());
+  EXPECT_EQ("{87efface-864d-49a5-9bb3-4b050a7c227a}", out.GetAppId());
+  EXPECT_EQ("0.2.2.3", out.app_version());
+  EXPECT_EQ("en-US", out.app_lang());
+  EXPECT_EQ(fake_system_state_.hardware()->GetHardwareClass(), out.hwid());
+  EXPECT_TRUE(out.delta_okay());
+  EXPECT_EQ("dev-channel", out.target_channel());
+  EXPECT_EQ("http://www.google.com", out.update_url());
+}
+
+TEST_F(OmahaRequestParamsTest, SetTargetChannelWorks) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=dev-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+
+  // Check LSB value is used by default when SetTargetChannel is not called.
+  params_.Init("", "", false);
+  EXPECT_EQ("dev-channel", params_.target_channel());
+
+  // When an invalid value is set, it should be ignored and the
+  // value from lsb-release should be used instead.
+  params_.Init("", "", false);
+  EXPECT_FALSE(params_.SetTargetChannel("invalid-channel", false, nullptr));
+  EXPECT_EQ("dev-channel", params_.target_channel());
+
+  // When set to a valid value, it should take effect.
+  params_.Init("", "", false);
+  EXPECT_TRUE(params_.SetTargetChannel("beta-channel", true, nullptr));
+  EXPECT_EQ("beta-channel", params_.target_channel());
+
+  // When set to the same value, it should be idempotent.
+  params_.Init("", "", false);
+  EXPECT_TRUE(params_.SetTargetChannel("beta-channel", true, nullptr));
+  EXPECT_EQ("beta-channel", params_.target_channel());
+
+  // When set to a valid value while a change is already pending, it should
+  // succeed.
+  params_.Init("", "", false);
+  EXPECT_TRUE(params_.SetTargetChannel("stable-channel", true, nullptr));
+  EXPECT_EQ("stable-channel", params_.target_channel());
+
+  // Set a different channel in stateful LSB release.
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"
+      "CHROMEOS_IS_POWERWASH_ALLOWED=true\n"));
+
+  // When set to a valid value while a change is already pending, it should
+  // succeed.
+  params_.Init("", "", false);
+  EXPECT_TRUE(params_.SetTargetChannel("beta-channel", true, nullptr));
+  // The target channel should reflect the change, but the download channel
+  // should continue to retain the old value ...
+  EXPECT_EQ("beta-channel", params_.target_channel());
+  EXPECT_EQ("stable-channel", params_.download_channel());
+
+  // ... until we update the download channel explicitly.
+  params_.UpdateDownloadChannel();
+  EXPECT_EQ("beta-channel", params_.download_channel());
+  EXPECT_EQ("beta-channel", params_.target_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, ChannelIndexTest) {
+  int canary = params_.GetChannelIndex("canary-channel");
+  int dev = params_.GetChannelIndex("dev-channel");
+  int beta = params_.GetChannelIndex("beta-channel");
+  int stable = params_.GetChannelIndex("stable-channel");
+  EXPECT_LE(canary, dev);
+  EXPECT_LE(dev, beta);
+  EXPECT_LE(beta, stable);
+
+  // testimage-channel or other names are not recognized, so index will be -1.
+  int testimage = params_.GetChannelIndex("testimage-channel");
+  int bogus = params_.GetChannelIndex("bogus-channel");
+  EXPECT_EQ(-1, testimage);
+  EXPECT_EQ(-1, bogus);
+}
+
+TEST_F(OmahaRequestParamsTest, ToMoreStableChannelFlagTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=arm-generic\n"
+      "CHROMEOS_RELEASE_FOO=bar\n"
+      "CHROMEOS_RELEASE_VERSION=0.2.2.3\n"
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"
+      "CHROMEOS_AUSERVER=http://www.google.com"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_BOARD=x86-generic\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"
+      "CHROMEOS_AUSERVER=https://www.google.com"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("https://www.google.com", out.update_url());
+  EXPECT_FALSE(out.delta_okay());
+  EXPECT_EQ("stable-channel", out.target_channel());
+  EXPECT_TRUE(out.to_more_stable_channel());
+}
+
+TEST_F(OmahaRequestParamsTest, BoardAppIdUsedForNonCanaryChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID=r\n"
+      "CHROMEOS_BOARD_APPID=b\n"
+      "CHROMEOS_CANARY_APPID=c\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("stable-channel", out.download_channel());
+  EXPECT_EQ("b", out.GetAppId());
+}
+
+TEST_F(OmahaRequestParamsTest, CanaryAppIdUsedForCanaryChannelTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID=r\n"
+      "CHROMEOS_BOARD_APPID=b\n"
+      "CHROMEOS_CANARY_APPID=c\n"
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("canary-channel", out.download_channel());
+  EXPECT_EQ("c", out.GetAppId());
+}
+
+TEST_F(OmahaRequestParamsTest, ReleaseAppIdUsedAsDefaultTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID=r\n"
+      "CHROMEOS_CANARY_APPID=c\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  OmahaRequestParams out(&fake_system_state_);
+  EXPECT_TRUE(DoTest(&out, "", ""));
+  EXPECT_EQ("stable-channel", out.download_channel());
+  EXPECT_EQ("r", out.GetAppId());
+}
+
+TEST_F(OmahaRequestParamsTest, CollectECFWVersionsTest) {
+  ASSERT_TRUE(WriteFileString(
+      test_dir_ + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_APPID=r\n"
+      "CHROMEOS_CANARY_APPID=c\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  OmahaRequestParams out(&fake_system_state_);
+  out.hwid_ = string("STUMPY ALEX 12345");
+  EXPECT_FALSE(out.CollectECFWVersions());
+
+  out.hwid_ = string("SNOW 12345");
+  EXPECT_TRUE(out.CollectECFWVersions());
+
+  out.hwid_ = string("SAMS ALEX 12345");
+  EXPECT_TRUE(out.CollectECFWVersions());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/omaha_response.h b/omaha_response.h
new file mode 100644
index 0000000..3a5a889
--- /dev/null
+++ b/omaha_response.h
@@ -0,0 +1,85 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_OMAHA_RESPONSE_H_
+#define UPDATE_ENGINE_OMAHA_RESPONSE_H_
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <string>
+#include <vector>
+
+namespace chromeos_update_engine {
+
+// This struct encapsulates the data Omaha's response for the request.
+// The strings in this struct are not XML escaped.
+struct OmahaResponse {
+  // True iff there is an update to be downloaded.
+  bool update_exists = false;
+
+  // If non-zero, server-dictated poll interval in seconds.
+  int poll_interval = 0;
+
+  // These are only valid if update_exists is true:
+  std::string version;
+
+  // The ordered list of URLs in the Omaha response. Each item is a complete
+  // URL (i.e. in terms of Omaha XML, each value is a urlBase + packageName)
+  std::vector<std::string> payload_urls;
+
+  std::string more_info_url;
+  std::string hash;
+  std::string metadata_signature;
+  std::string deadline;
+  off_t size = 0;
+  off_t metadata_size = 0;
+  int max_days_to_scatter = 0;
+  // The number of URL-related failures to tolerate before moving on to the
+  // next URL in the current pass. This is a configurable value from the
+  // Omaha Response attribute, if ever we need to fine tune the behavior.
+  uint32_t max_failure_count_per_url = 0;
+  bool prompt = false;
+
+  // True if the payload described in this response is a delta payload.
+  // False if it's a full payload.
+  bool is_delta_payload = false;
+
+  // True if the Omaha rule instructs us to disable the back-off logic
+  // on the client altogether. False otherwise.
+  bool disable_payload_backoff = false;
+
+  // True if the Omaha rule instructs us to disable p2p for downloading.
+  bool disable_p2p_for_downloading = false;
+
+  // True if the Omaha rule instructs us to disable p2p for sharing.
+  bool disable_p2p_for_sharing = false;
+
+  // If not blank, a base-64 encoded representation of the PEM-encoded
+  // public key in the response.
+  std::string public_key_rsa;
+
+  // If not -1, the number of days since the epoch Jan 1, 2007 0:00
+  // PST, according to the Omaha Server's clock and timezone (PST8PDT,
+  // aka "Pacific Time".)
+  int install_date_days = -1;
+};
+COMPILE_ASSERT(sizeof(off_t) == 8, off_t_not_64bit);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_OMAHA_RESPONSE_H_
diff --git a/omaha_response_handler_action.cc b/omaha_response_handler_action.cc
new file mode 100644
index 0000000..3fa9348
--- /dev/null
+++ b/omaha_response_handler_action.cc
@@ -0,0 +1,206 @@
+//
+// Copyright (C) 2011 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 "update_engine/omaha_response_handler_action.h"
+
+#include <string>
+
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <policy/device_policy.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/connection_manager_interface.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_state_interface.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+OmahaResponseHandlerAction::OmahaResponseHandlerAction(
+    SystemState* system_state)
+    : OmahaResponseHandlerAction(system_state,
+                                 constants::kOmahaResponseDeadlineFile) {}
+
+OmahaResponseHandlerAction::OmahaResponseHandlerAction(
+    SystemState* system_state, const string& deadline_file)
+    : system_state_(system_state),
+      got_no_update_response_(false),
+      key_path_(constants::kUpdatePayloadPublicKeyPath),
+      deadline_file_(deadline_file) {}
+
+void OmahaResponseHandlerAction::PerformAction() {
+  CHECK(HasInputObject());
+  ScopedActionCompleter completer(processor_, this);
+  const OmahaResponse& response = GetInputObject();
+  if (!response.update_exists) {
+    got_no_update_response_ = true;
+    LOG(INFO) << "There are no updates. Aborting.";
+    return;
+  }
+
+  // All decisions as to which URL should be used have already been done. So,
+  // make the current URL as the download URL.
+  string current_url = system_state_->payload_state()->GetCurrentUrl();
+  if (current_url.empty()) {
+    // This shouldn't happen as we should always supply the HTTPS backup URL.
+    // Handling this anyway, just in case.
+    LOG(ERROR) << "There are no suitable URLs in the response to use.";
+    completer.set_code(ErrorCode::kOmahaResponseInvalid);
+    return;
+  }
+
+  install_plan_.download_url = current_url;
+  install_plan_.version = response.version;
+
+  OmahaRequestParams* const params = system_state_->request_params();
+  PayloadStateInterface* const payload_state = system_state_->payload_state();
+
+  // If we're using p2p to download and there is a local peer, use it.
+  if (payload_state->GetUsingP2PForDownloading() &&
+      !payload_state->GetP2PUrl().empty()) {
+    LOG(INFO) << "Replacing URL " << install_plan_.download_url
+              << " with local URL " << payload_state->GetP2PUrl()
+              << " since p2p is enabled.";
+    install_plan_.download_url = payload_state->GetP2PUrl();
+    payload_state->SetUsingP2PForDownloading(true);
+  }
+
+  // Fill up the other properties based on the response.
+  install_plan_.payload_size = response.size;
+  install_plan_.payload_hash = response.hash;
+  install_plan_.metadata_size = response.metadata_size;
+  install_plan_.metadata_signature = response.metadata_signature;
+  install_plan_.public_key_rsa = response.public_key_rsa;
+  install_plan_.hash_checks_mandatory = AreHashChecksMandatory(response);
+  install_plan_.is_resume =
+      DeltaPerformer::CanResumeUpdate(system_state_->prefs(), response.hash);
+  if (install_plan_.is_resume) {
+    payload_state->UpdateResumed();
+  } else {
+    payload_state->UpdateRestarted();
+    LOG_IF(WARNING, !DeltaPerformer::ResetUpdateProgress(
+        system_state_->prefs(), false))
+        << "Unable to reset the update progress.";
+    LOG_IF(WARNING, !system_state_->prefs()->SetString(
+        kPrefsUpdateCheckResponseHash, response.hash))
+        << "Unable to save the update check response hash.";
+  }
+  install_plan_.is_full_update = !response.is_delta_payload;
+
+  install_plan_.source_slot = system_state_->boot_control()->GetCurrentSlot();
+  install_plan_.target_slot = install_plan_.source_slot == 0 ? 1 : 0;
+
+  // The Omaha response doesn't include the channel name for this image, so we
+  // use the download_channel we used during the request to tag the target slot.
+  // This will be used in the next boot to know the channel the image was
+  // downloaded from.
+  string current_channel_key =
+      kPrefsChannelOnSlotPrefix + std::to_string(install_plan_.target_slot);
+  system_state_->prefs()->SetString(current_channel_key,
+                                    params->download_channel());
+
+  if (params->to_more_stable_channel() && params->is_powerwash_allowed())
+    install_plan_.powerwash_required = true;
+
+  TEST_AND_RETURN(HasOutputPipe());
+  if (HasOutputPipe())
+    SetOutputObject(install_plan_);
+  LOG(INFO) << "Using this install plan:";
+  install_plan_.Dump();
+
+  // Send the deadline data (if any) to Chrome through a file. This is a pretty
+  // hacky solution but should be OK for now.
+  //
+  // TODO(petkov): Re-architect this to avoid communication through a
+  // file. Ideally, we would include this information in D-Bus's GetStatus
+  // method and UpdateStatus signal. A potential issue is that update_engine may
+  // be unresponsive during an update download.
+  if (!deadline_file_.empty()) {
+    utils::WriteFile(deadline_file_.c_str(),
+                     response.deadline.data(),
+                     response.deadline.size());
+    chmod(deadline_file_.c_str(), S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
+  }
+
+  completer.set_code(ErrorCode::kSuccess);
+}
+
+bool OmahaResponseHandlerAction::AreHashChecksMandatory(
+    const OmahaResponse& response) {
+  // We sometimes need to waive the hash checks in order to download from
+  // sources that don't provide hashes, such as dev server.
+  // At this point UpdateAttempter::IsAnyUpdateSourceAllowed() has already been
+  // checked, so an unofficial update URL won't get this far unless it's OK to
+  // use without a hash. Additionally, we want to always waive hash checks on
+  // unofficial builds (i.e. dev/test images).
+  // The end result is this:
+  //  * Base image:
+  //    - Official URLs require a hash.
+  //    - Unofficial URLs only get this far if the IsAnyUpdateSourceAllowed()
+  //      devmode/debugd checks pass, in which case the hash is waived.
+  //  * Dev/test image:
+  //    - Any URL is allowed through with no hash checking.
+  if (!system_state_->request_params()->IsUpdateUrlOfficial() ||
+      !system_state_->hardware()->IsOfficialBuild()) {
+    // Still do a hash check if a public key is included.
+    if (!response.public_key_rsa.empty()) {
+      // The autoupdate_CatchBadSignatures test checks for this string
+      // in log-files. Keep in sync.
+      LOG(INFO) << "Mandating payload hash checks since Omaha Response "
+                << "for unofficial build includes public RSA key.";
+      return true;
+    } else {
+      LOG(INFO) << "Waiving payload hash checks for unofficial update URL.";
+      return false;
+    }
+  }
+
+  // If we're using p2p, |install_plan_.download_url| may contain a
+  // HTTP URL even if |response.payload_urls| contain only HTTPS URLs.
+  if (!base::StartsWithASCII(install_plan_.download_url, "https://", false)) {
+    LOG(INFO) << "Mandating hash checks since download_url is not HTTPS.";
+    return true;
+  }
+
+  // TODO(jaysri): VALIDATION: For official builds, we currently waive hash
+  // checks for HTTPS until we have rolled out at least once and are confident
+  // nothing breaks. chromium-os:37082 tracks turning this on for HTTPS
+  // eventually.
+
+  // Even if there's a single non-HTTPS URL, make the hash checks as
+  // mandatory because we could be downloading the payload from any URL later
+  // on. It's really hard to do book-keeping based on each byte being
+  // downloaded to see whether we only used HTTPS throughout.
+  for (size_t i = 0; i < response.payload_urls.size(); i++) {
+    if (!base::StartsWithASCII(response.payload_urls[i], "https://", false)) {
+      LOG(INFO) << "Mandating payload hash checks since Omaha response "
+                << "contains non-HTTPS URL(s)";
+      return true;
+    }
+  }
+
+  LOG(INFO) << "Waiving payload hash checks since Omaha response "
+            << "only has HTTPS URL(s)";
+  return false;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/omaha_response_handler_action.h b/omaha_response_handler_action.h
new file mode 100644
index 0000000..51dfa7a
--- /dev/null
+++ b/omaha_response_handler_action.h
@@ -0,0 +1,98 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_OMAHA_RESPONSE_HANDLER_ACTION_H_
+#define UPDATE_ENGINE_OMAHA_RESPONSE_HANDLER_ACTION_H_
+
+#include <string>
+
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/action.h"
+#include "update_engine/omaha_request_action.h"
+#include "update_engine/payload_consumer/install_plan.h"
+#include "update_engine/system_state.h"
+
+// This class reads in an Omaha response and converts what it sees into
+// an install plan which is passed out.
+
+namespace chromeos_update_engine {
+
+class OmahaResponseHandlerAction;
+
+template<>
+class ActionTraits<OmahaResponseHandlerAction> {
+ public:
+  typedef OmahaResponse InputObjectType;
+  typedef InstallPlan OutputObjectType;
+};
+
+class OmahaResponseHandlerAction : public Action<OmahaResponseHandlerAction> {
+ public:
+  explicit OmahaResponseHandlerAction(SystemState* system_state);
+
+  typedef ActionTraits<OmahaResponseHandlerAction>::InputObjectType
+      InputObjectType;
+  typedef ActionTraits<OmahaResponseHandlerAction>::OutputObjectType
+      OutputObjectType;
+  void PerformAction() override;
+
+  // This is a synchronous action, and thus TerminateProcessing() should
+  // never be called
+  void TerminateProcessing() override { CHECK(false); }
+
+  bool GotNoUpdateResponse() const { return got_no_update_response_; }
+  const InstallPlan& install_plan() const { return install_plan_; }
+
+  // Debugging/logging
+  static std::string StaticType() { return "OmahaResponseHandlerAction"; }
+  std::string Type() const override { return StaticType(); }
+  void set_key_path(const std::string& path) { key_path_ = path; }
+
+ private:
+  // Returns true if payload hash checks are mandatory based on the state
+  // of the system and the contents of the Omaha response. False otherwise.
+  bool AreHashChecksMandatory(const OmahaResponse& response);
+
+  // Global system context.
+  SystemState* system_state_;
+
+  // The install plan, if we have an update.
+  InstallPlan install_plan_;
+
+  // True only if we got a response and the response said no updates
+  bool got_no_update_response_;
+
+  // Public key path to use for payload verification.
+  std::string key_path_;
+
+  // File used for communication deadline to Chrome.
+  const std::string deadline_file_;
+
+  // Special ctor + friend declarations for testing purposes.
+  OmahaResponseHandlerAction(SystemState* system_state,
+                             const std::string& deadline_file);
+
+  friend class OmahaResponseHandlerActionTest;
+
+  FRIEND_TEST(UpdateAttempterTest, CreatePendingErrorEventResumedTest);
+
+  DISALLOW_COPY_AND_ASSIGN(OmahaResponseHandlerAction);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_OMAHA_RESPONSE_HANDLER_ACTION_H_
diff --git a/omaha_response_handler_action_unittest.cc b/omaha_response_handler_action_unittest.cc
new file mode 100644
index 0000000..b996d38
--- /dev/null
+++ b/omaha_response_handler_action_unittest.cc
@@ -0,0 +1,435 @@
+//
+// Copyright (C) 2011 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 "update_engine/omaha_response_handler_action.h"
+
+#include <string>
+
+#include <base/files/file_util.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/mock_payload_state.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using chromeos_update_engine::test_utils::System;
+using chromeos_update_engine::test_utils::WriteFileString;
+using std::string;
+using testing::Return;
+
+namespace chromeos_update_engine {
+
+class OmahaResponseHandlerActionTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    FakeBootControl* fake_boot_control = fake_system_state_.fake_boot_control();
+    fake_boot_control->SetPartitionDevice(
+        kLegacyPartitionNameKernel, 0, "/dev/sdz2");
+    fake_boot_control->SetPartitionDevice(
+        kLegacyPartitionNameRoot, 0, "/dev/sdz3");
+    fake_boot_control->SetPartitionDevice(
+        kLegacyPartitionNameKernel, 1, "/dev/sdz4");
+    fake_boot_control->SetPartitionDevice(
+        kLegacyPartitionNameRoot, 1, "/dev/sdz5");
+  }
+
+  // Return true iff the OmahaResponseHandlerAction succeeded.
+  // If out is non-null, it's set w/ the response from the action.
+  bool DoTest(const OmahaResponse& in,
+              const string& deadline_file,
+              InstallPlan* out);
+
+  FakeSystemState fake_system_state_;
+};
+
+class OmahaResponseHandlerActionProcessorDelegate
+    : public ActionProcessorDelegate {
+ public:
+  OmahaResponseHandlerActionProcessorDelegate()
+      : code_(ErrorCode::kError),
+        code_set_(false) {}
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) {
+    if (action->Type() == OmahaResponseHandlerAction::StaticType()) {
+      code_ = code;
+      code_set_ = true;
+    }
+  }
+  ErrorCode code_;
+  bool code_set_;
+};
+
+namespace {
+const char* const kLongName =
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "very_long_name_and_no_slashes-very_long_name_and_no_slashes"
+    "-the_update_a.b.c.d_DELTA_.tgz";
+const char* const kBadVersion = "don't update me";
+}  // namespace
+
+bool OmahaResponseHandlerActionTest::DoTest(
+    const OmahaResponse& in,
+    const string& test_deadline_file,
+    InstallPlan* out) {
+  ActionProcessor processor;
+  OmahaResponseHandlerActionProcessorDelegate delegate;
+  processor.set_delegate(&delegate);
+
+  ObjectFeederAction<OmahaResponse> feeder_action;
+  feeder_action.set_obj(in);
+  if (in.update_exists && in.version != kBadVersion) {
+    EXPECT_CALL(*(fake_system_state_.mock_prefs()),
+                SetString(kPrefsUpdateCheckResponseHash, in.hash))
+        .WillOnce(Return(true));
+
+    int slot = 1 - fake_system_state_.fake_boot_control()->GetCurrentSlot();
+    string key = kPrefsChannelOnSlotPrefix + std::to_string(slot);
+    EXPECT_CALL(*(fake_system_state_.mock_prefs()), SetString(key, testing::_))
+        .WillOnce(Return(true));
+  }
+
+  string current_url = in.payload_urls.size() ? in.payload_urls[0] : "";
+  EXPECT_CALL(*(fake_system_state_.mock_payload_state()), GetCurrentUrl())
+      .WillRepeatedly(Return(current_url));
+
+  OmahaResponseHandlerAction response_handler_action(
+      &fake_system_state_,
+      (test_deadline_file.empty() ?
+       constants::kOmahaResponseDeadlineFile : test_deadline_file));
+  BondActions(&feeder_action, &response_handler_action);
+  ObjectCollectorAction<InstallPlan> collector_action;
+  BondActions(&response_handler_action, &collector_action);
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&response_handler_action);
+  processor.EnqueueAction(&collector_action);
+  processor.StartProcessing();
+  EXPECT_TRUE(!processor.IsRunning())
+      << "Update test to handle non-async actions";
+  if (out)
+    *out = collector_action.object();
+  EXPECT_TRUE(delegate.code_set_);
+  return delegate.code_ == ErrorCode::kSuccess;
+}
+
+TEST_F(OmahaResponseHandlerActionTest, SimpleTest) {
+  string test_deadline_file;
+  CHECK(utils::MakeTempFile(
+          "omaha_response_handler_action_unittest-XXXXXX",
+          &test_deadline_file, nullptr));
+  ScopedPathUnlinker deadline_unlinker(test_deadline_file);
+  {
+    OmahaResponse in;
+    in.update_exists = true;
+    in.version = "a.b.c.d";
+    in.payload_urls.push_back("http://foo/the_update_a.b.c.d.tgz");
+    in.more_info_url = "http://more/info";
+    in.hash = "HASH+";
+    in.size = 12;
+    in.prompt = false;
+    in.deadline = "20101020";
+    InstallPlan install_plan;
+    EXPECT_TRUE(DoTest(in, test_deadline_file, &install_plan));
+    EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+    EXPECT_EQ(in.hash, install_plan.payload_hash);
+    EXPECT_EQ(1, install_plan.target_slot);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFile(test_deadline_file, &deadline));
+    EXPECT_EQ("20101020", deadline);
+    struct stat deadline_stat;
+    EXPECT_EQ(0, stat(test_deadline_file.c_str(), &deadline_stat));
+    EXPECT_EQ(S_IFREG | S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH,
+              deadline_stat.st_mode);
+    EXPECT_EQ(in.version, install_plan.version);
+  }
+  {
+    OmahaResponse in;
+    in.update_exists = true;
+    in.version = "a.b.c.d";
+    in.payload_urls.push_back("http://foo/the_update_a.b.c.d.tgz");
+    in.more_info_url = "http://more/info";
+    in.hash = "HASHj+";
+    in.size = 12;
+    in.prompt = true;
+    InstallPlan install_plan;
+    // Set the other slot as current.
+    fake_system_state_.fake_boot_control()->SetCurrentSlot(1);
+    EXPECT_TRUE(DoTest(in, test_deadline_file, &install_plan));
+    EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+    EXPECT_EQ(in.hash, install_plan.payload_hash);
+    EXPECT_EQ(0, install_plan.target_slot);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFile(test_deadline_file, &deadline) &&
+                deadline.empty());
+    EXPECT_EQ(in.version, install_plan.version);
+  }
+  {
+    OmahaResponse in;
+    in.update_exists = true;
+    in.version = "a.b.c.d";
+    in.payload_urls.push_back(kLongName);
+    in.more_info_url = "http://more/info";
+    in.hash = "HASHj+";
+    in.size = 12;
+    in.prompt = true;
+    in.deadline = "some-deadline";
+    InstallPlan install_plan;
+    fake_system_state_.fake_boot_control()->SetCurrentSlot(0);
+    EXPECT_TRUE(DoTest(in, test_deadline_file, &install_plan));
+    EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+    EXPECT_EQ(in.hash, install_plan.payload_hash);
+    EXPECT_EQ(1, install_plan.target_slot);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFile(test_deadline_file, &deadline));
+    EXPECT_EQ("some-deadline", deadline);
+    EXPECT_EQ(in.version, install_plan.version);
+  }
+}
+
+TEST_F(OmahaResponseHandlerActionTest, NoUpdatesTest) {
+  OmahaResponse in;
+  in.update_exists = false;
+  InstallPlan install_plan;
+  EXPECT_FALSE(DoTest(in, "", &install_plan));
+  EXPECT_TRUE(install_plan.partitions.empty());
+}
+
+TEST_F(OmahaResponseHandlerActionTest, HashChecksForHttpTest) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("http://test.should/need/hash.checks.signed");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+  // Hash checks are always skipped for non-official update URLs.
+  EXPECT_CALL(*(fake_system_state_.mock_request_params()),
+              IsUpdateUrlOfficial())
+      .WillRepeatedly(Return(true));
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_TRUE(install_plan.hash_checks_mandatory);
+  EXPECT_EQ(in.version, install_plan.version);
+}
+
+TEST_F(OmahaResponseHandlerActionTest, HashChecksForUnofficialUpdateUrl) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("http://url.normally/needs/hash.checks.signed");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+  EXPECT_CALL(*(fake_system_state_.mock_request_params()),
+              IsUpdateUrlOfficial())
+      .WillRepeatedly(Return(false));
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_FALSE(install_plan.hash_checks_mandatory);
+  EXPECT_EQ(in.version, install_plan.version);
+}
+
+TEST_F(OmahaResponseHandlerActionTest,
+       HashChecksForOfficialUrlUnofficialBuildTest) {
+  // Official URLs for unofficial builds (dev/test images) don't require hash.
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("http://url.normally/needs/hash.checks.signed");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+  EXPECT_CALL(*(fake_system_state_.mock_request_params()),
+              IsUpdateUrlOfficial())
+      .WillRepeatedly(Return(true));
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(false);
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_FALSE(install_plan.hash_checks_mandatory);
+  EXPECT_EQ(in.version, install_plan.version);
+}
+
+TEST_F(OmahaResponseHandlerActionTest, HashChecksForHttpsTest) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("https://test.should.not/need/hash.checks.signed");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+  EXPECT_CALL(*(fake_system_state_.mock_request_params()),
+              IsUpdateUrlOfficial())
+      .WillRepeatedly(Return(true));
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_FALSE(install_plan.hash_checks_mandatory);
+  EXPECT_EQ(in.version, install_plan.version);
+}
+
+TEST_F(OmahaResponseHandlerActionTest, HashChecksForBothHttpAndHttpsTest) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("http://test.should.still/need/hash.checks");
+  in.payload_urls.push_back("https://test.should.still/need/hash.checks");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+  EXPECT_CALL(*(fake_system_state_.mock_request_params()),
+              IsUpdateUrlOfficial())
+      .WillRepeatedly(Return(true));
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.payload_urls[0], install_plan.download_url);
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_TRUE(install_plan.hash_checks_mandatory);
+  EXPECT_EQ(in.version, install_plan.version);
+}
+
+TEST_F(OmahaResponseHandlerActionTest, ChangeToMoreStableChannelTest) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("https://MoreStableChannelTest");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHjk";
+  in.size = 15;
+
+  // Create a uniquely named test directory.
+  string test_dir;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          "omaha_response_handler_action-test-XXXXXX", &test_dir));
+
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir + "/etc"));
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir +
+                      kStatefulPartition + "/etc"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_IS_POWERWASH_ALLOWED=true\n"
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+
+  OmahaRequestParams params(&fake_system_state_);
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(false);
+  params.set_root(test_dir);
+  params.Init("1.2.3.4", "", 0);
+  EXPECT_EQ("canary-channel", params.current_channel());
+  EXPECT_EQ("stable-channel", params.target_channel());
+  EXPECT_TRUE(params.to_more_stable_channel());
+  EXPECT_TRUE(params.is_powerwash_allowed());
+
+  fake_system_state_.set_request_params(&params);
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_TRUE(install_plan.powerwash_required);
+
+  ASSERT_TRUE(base::DeleteFile(base::FilePath(test_dir), true));
+}
+
+TEST_F(OmahaResponseHandlerActionTest, ChangeToLessStableChannelTest) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("https://LessStableChannelTest");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHjk";
+  in.size = 15;
+
+  // Create a uniquely named test directory.
+  string test_dir;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          "omaha_response_handler_action-test-XXXXXX", &test_dir));
+
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir + "/etc"));
+  ASSERT_EQ(0, System(string("mkdir -p ") + test_dir +
+                      kStatefulPartition + "/etc"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_TRACK=stable-channel\n"));
+  ASSERT_TRUE(WriteFileString(
+      test_dir + kStatefulPartition + "/etc/lsb-release",
+      "CHROMEOS_RELEASE_TRACK=canary-channel\n"));
+
+  OmahaRequestParams params(&fake_system_state_);
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(false);
+  params.set_root(test_dir);
+  params.Init("5.6.7.8", "", 0);
+  EXPECT_EQ("stable-channel", params.current_channel());
+  params.SetTargetChannel("canary-channel", false, nullptr);
+  EXPECT_EQ("canary-channel", params.target_channel());
+  EXPECT_FALSE(params.to_more_stable_channel());
+  EXPECT_FALSE(params.is_powerwash_allowed());
+
+  fake_system_state_.set_request_params(&params);
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_FALSE(install_plan.powerwash_required);
+
+  ASSERT_TRUE(base::DeleteFile(base::FilePath(test_dir), true));
+}
+
+TEST_F(OmahaResponseHandlerActionTest, P2PUrlIsUsedAndHashChecksMandatory) {
+  OmahaResponse in;
+  in.update_exists = true;
+  in.version = "a.b.c.d";
+  in.payload_urls.push_back("https://would.not/cause/hash/checks");
+  in.more_info_url = "http://more/info";
+  in.hash = "HASHj+";
+  in.size = 12;
+
+  OmahaRequestParams params(&fake_system_state_);
+  // We're using a real OmahaRequestParams object here so we can't mock
+  // IsUpdateUrlOfficial(), but setting the update URL to the AutoUpdate test
+  // server will cause IsUpdateUrlOfficial() to return true.
+  params.set_update_url(constants::kOmahaDefaultAUTestURL);
+  fake_system_state_.set_request_params(&params);
+
+  EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+              SetUsingP2PForDownloading(true));
+
+  string p2p_url = "http://9.8.7.6/p2p";
+  EXPECT_CALL(*fake_system_state_.mock_payload_state(), GetP2PUrl())
+      .WillRepeatedly(Return(p2p_url));
+  EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+              GetUsingP2PForDownloading()).WillRepeatedly(Return(true));
+
+  InstallPlan install_plan;
+  EXPECT_TRUE(DoTest(in, "", &install_plan));
+  EXPECT_EQ(in.hash, install_plan.payload_hash);
+  EXPECT_EQ(install_plan.download_url, p2p_url);
+  EXPECT_TRUE(install_plan.hash_checks_mandatory);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/p2p_manager.cc b/p2p_manager.cc
new file mode 100644
index 0000000..658630c
--- /dev/null
+++ b/p2p_manager.cc
@@ -0,0 +1,736 @@
+//
+// Copyright (C) 2013 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.
+//
+
+// This provides access to timestamps with nanosecond resolution in
+// struct stat, See NOTES in stat(2) for details.
+#ifndef _BSD_SOURCE
+#define _BSD_SOURCE
+#endif
+
+#include "update_engine/p2p_manager.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <linux/falloc.h>
+#include <signal.h>
+#include <string.h>
+#include <sys/stat.h>
+#include <sys/statvfs.h>
+#include <sys/types.h>
+#include <sys/xattr.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <map>
+#include <memory>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/files/file_enumerator.h>
+#include <base/files/file_path.h>
+#include <base/format_macros.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/update_manager.h"
+
+using base::Bind;
+using base::Callback;
+using base::FilePath;
+using base::StringPrintf;
+using base::Time;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using chromeos_update_manager::EvalStatus;
+using chromeos_update_manager::Policy;
+using chromeos_update_manager::UpdateManager;
+using std::map;
+using std::pair;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// The default p2p directory.
+const char kDefaultP2PDir[] = "/var/cache/p2p";
+
+// The p2p xattr used for conveying the final size of a file - see the
+// p2p ddoc for details.
+const char kCrosP2PFileSizeXAttrName[] = "user.cros-p2p-filesize";
+
+}  // namespace
+
+// The default P2PManager::Configuration implementation.
+class ConfigurationImpl : public P2PManager::Configuration {
+ public:
+  ConfigurationImpl() {}
+
+  FilePath GetP2PDir() override {
+    return FilePath(kDefaultP2PDir);
+  }
+
+  vector<string> GetInitctlArgs(bool is_start) override {
+    vector<string> args;
+    args.push_back("initctl");
+    args.push_back(is_start ? "start" : "stop");
+    args.push_back("p2p");
+    return args;
+  }
+
+  vector<string> GetP2PClientArgs(const string &file_id,
+                                  size_t minimum_size) override {
+    vector<string> args;
+    args.push_back("p2p-client");
+    args.push_back(string("--get-url=") + file_id);
+    args.push_back(StringPrintf("--minimum-size=%" PRIuS, minimum_size));
+    return args;
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ConfigurationImpl);
+};
+
+// The default P2PManager implementation.
+class P2PManagerImpl : public P2PManager {
+ public:
+  P2PManagerImpl(Configuration *configuration,
+                 ClockInterface *clock,
+                 UpdateManager* update_manager,
+                 const string& file_extension,
+                 const int num_files_to_keep,
+                 const TimeDelta& max_file_age);
+
+  // P2PManager methods.
+  void SetDevicePolicy(const policy::DevicePolicy* device_policy) override;
+  bool IsP2PEnabled() override;
+  bool EnsureP2PRunning() override;
+  bool EnsureP2PNotRunning() override;
+  bool PerformHousekeeping() override;
+  void LookupUrlForFile(const string& file_id,
+                        size_t minimum_size,
+                        TimeDelta max_time_to_wait,
+                        LookupCallback callback) override;
+  bool FileShare(const string& file_id,
+                 size_t expected_size) override;
+  FilePath FileGetPath(const string& file_id) override;
+  ssize_t FileGetSize(const string& file_id) override;
+  ssize_t FileGetExpectedSize(const string& file_id) override;
+  bool FileGetVisible(const string& file_id,
+                      bool *out_result) override;
+  bool FileMakeVisible(const string& file_id) override;
+  int CountSharedFiles() override;
+
+ private:
+  // Enumeration for specifying visibility.
+  enum Visibility {
+    kVisible,
+    kNonVisible
+  };
+
+  // Returns "." + |file_extension_| + ".p2p" if |visibility| is
+  // |kVisible|. Returns the same concatenated with ".tmp" otherwise.
+  string GetExt(Visibility visibility);
+
+  // Gets the on-disk path for |file_id| depending on if the file
+  // is visible or not.
+  FilePath GetPath(const string& file_id, Visibility visibility);
+
+  // Utility function used by EnsureP2PRunning() and EnsureP2PNotRunning().
+  bool EnsureP2P(bool should_be_running);
+
+  // Utility function to delete a file given by |path| and log the
+  // path as well as |reason|. Returns false on failure.
+  bool DeleteP2PFile(const FilePath& path, const string& reason);
+
+  // Schedules an async request for tracking changes in P2P enabled status.
+  void ScheduleEnabledStatusChange();
+
+  // An async callback used by the above.
+  void OnEnabledStatusChange(EvalStatus status, const bool& result);
+
+  // The device policy being used or null if no policy is being used.
+  const policy::DevicePolicy* device_policy_ = nullptr;
+
+  // Configuration object.
+  unique_ptr<Configuration> configuration_;
+
+  // Object for telling the time.
+  ClockInterface* clock_;
+
+  // A pointer to the global Update Manager.
+  UpdateManager* update_manager_;
+
+  // A short string unique to the application (for example "cros_au")
+  // used to mark a file as being owned by a particular application.
+  const string file_extension_;
+
+  // If non-zero, this number denotes how many files in /var/cache/p2p
+  // owned by the application (cf. |file_extension_|) to keep after
+  // performing housekeeping.
+  const int num_files_to_keep_;
+
+  // If non-zero, files older than this will not be kept after
+  // performing housekeeping.
+  const TimeDelta max_file_age_;
+
+  // The string ".p2p".
+  static const char kP2PExtension[];
+
+  // The string ".tmp".
+  static const char kTmpExtension[];
+
+  // Whether P2P service may be running; initially, we assume it may be.
+  bool may_be_running_ = true;
+
+  // The current known enabled status of the P2P feature (initialized lazily),
+  // and whether an async status check has been scheduled.
+  bool is_enabled_;
+  bool waiting_for_enabled_status_change_ = false;
+
+  DISALLOW_COPY_AND_ASSIGN(P2PManagerImpl);
+};
+
+const char P2PManagerImpl::kP2PExtension[] = ".p2p";
+
+const char P2PManagerImpl::kTmpExtension[] = ".tmp";
+
+P2PManagerImpl::P2PManagerImpl(Configuration *configuration,
+                               ClockInterface *clock,
+                               UpdateManager* update_manager,
+                               const string& file_extension,
+                               const int num_files_to_keep,
+                               const TimeDelta& max_file_age)
+  : clock_(clock),
+    update_manager_(update_manager),
+    file_extension_(file_extension),
+    num_files_to_keep_(num_files_to_keep),
+    max_file_age_(max_file_age) {
+  configuration_.reset(configuration != nullptr ? configuration :
+                       new ConfigurationImpl());
+}
+
+void P2PManagerImpl::SetDevicePolicy(
+    const policy::DevicePolicy* device_policy) {
+  device_policy_ = device_policy;
+}
+
+bool P2PManagerImpl::IsP2PEnabled() {
+  if (!waiting_for_enabled_status_change_) {
+    // Get and store an initial value.
+    if (update_manager_->PolicyRequest(&Policy::P2PEnabled, &is_enabled_) ==
+        EvalStatus::kFailed) {
+      is_enabled_ = false;
+      LOG(ERROR) << "Querying P2P enabled status failed, disabling.";
+    }
+
+    // Track future changes (async).
+    ScheduleEnabledStatusChange();
+  }
+
+  return is_enabled_;
+}
+
+bool P2PManagerImpl::EnsureP2P(bool should_be_running) {
+  int return_code = 0;
+  string output;
+
+  may_be_running_ = true;  // Unless successful, we must be conservative.
+
+  vector<string> args = configuration_->GetInitctlArgs(should_be_running);
+  if (!Subprocess::SynchronousExec(args, &return_code, &output)) {
+    LOG(ERROR) << "Error spawning " << utils::StringVectorToString(args);
+    return false;
+  }
+
+  // If initctl(8) does not exit normally (exit status other than zero), ensure
+  // that the error message is not benign by scanning stderr; this is a
+  // necessity because initctl does not offer actions such as "start if not
+  // running" or "stop if running".
+  // TODO(zeuthen,chromium:277051): Avoid doing this.
+  if (return_code != 0) {
+    const char *expected_error_message = should_be_running ?
+      "initctl: Job is already running: p2p\n" :
+      "initctl: Unknown instance \n";
+    if (output != expected_error_message)
+      return false;
+  }
+
+  may_be_running_ = should_be_running;  // Successful after all.
+  return true;
+}
+
+bool P2PManagerImpl::EnsureP2PRunning() {
+  return EnsureP2P(true);
+}
+
+bool P2PManagerImpl::EnsureP2PNotRunning() {
+  return EnsureP2P(false);
+}
+
+// Returns True if the timestamp in the first pair is greater than the
+// timestamp in the latter. If used with std::sort() this will yield a
+// sequence of elements where newer (high timestamps) elements precede
+// older ones (low timestamps).
+static bool MatchCompareFunc(const pair<FilePath, Time>& a,
+                             const pair<FilePath, Time>& b) {
+  return a.second > b.second;
+}
+
+string P2PManagerImpl::GetExt(Visibility visibility) {
+  string ext = string(".") + file_extension_ + kP2PExtension;
+  switch (visibility) {
+  case kVisible:
+    break;
+  case kNonVisible:
+    ext += kTmpExtension;
+    break;
+  // Don't add a default case to let the compiler warn about newly
+  // added enum values.
+  }
+  return ext;
+}
+
+FilePath P2PManagerImpl::GetPath(const string& file_id, Visibility visibility) {
+  return configuration_->GetP2PDir().Append(file_id + GetExt(visibility));
+}
+
+bool P2PManagerImpl::DeleteP2PFile(const FilePath& path,
+                                   const string& reason) {
+  LOG(INFO) << "Deleting p2p file " << path.value()
+            << " (reason: " << reason << ")";
+  if (unlink(path.value().c_str()) != 0) {
+    PLOG(ERROR) << "Error deleting p2p file " << path.value();
+    return false;
+  }
+  return true;
+}
+
+
+bool P2PManagerImpl::PerformHousekeeping() {
+  // Open p2p dir.
+  FilePath p2p_dir = configuration_->GetP2PDir();
+  const string ext_visible = GetExt(kVisible);
+  const string ext_non_visible = GetExt(kNonVisible);
+
+  bool deletion_failed = false;
+  vector<pair<FilePath, Time>> matches;
+
+  base::FileEnumerator dir(p2p_dir, false, base::FileEnumerator::FILES);
+  // Go through all files and collect their mtime.
+  for (FilePath name = dir.Next(); !name.empty(); name = dir.Next()) {
+    if (!(base::EndsWith(name.value(), ext_visible, true) ||
+          base::EndsWith(name.value(), ext_non_visible, true)))
+      continue;
+
+    Time time = dir.GetInfo().GetLastModifiedTime();
+
+    // If instructed to keep only files younger than a given age
+    // (|max_file_age_| != 0), delete files satisfying this criteria
+    // right now. Otherwise add it to a list we'll consider for later.
+    if (clock_ != nullptr && max_file_age_ != TimeDelta() &&
+        clock_->GetWallclockTime() - time > max_file_age_) {
+      if (!DeleteP2PFile(name, "file too old"))
+        deletion_failed = true;
+    } else {
+      matches.push_back(std::make_pair(name, time));
+    }
+  }
+
+  // If instructed to only keep N files (|max_files_to_keep_ != 0),
+  // sort list of matches, newest (biggest time) to oldest (lowest
+  // time). Then delete starting at element |num_files_to_keep_|.
+  if (num_files_to_keep_ > 0) {
+    std::sort(matches.begin(), matches.end(), MatchCompareFunc);
+    vector<pair<FilePath, Time>>::const_iterator i;
+    for (i = matches.begin() + num_files_to_keep_; i < matches.end(); ++i) {
+      if (!DeleteP2PFile(i->first, "too many files"))
+        deletion_failed = true;
+    }
+  }
+
+  return !deletion_failed;
+}
+
+// Helper class for implementing LookupUrlForFile().
+class LookupData {
+ public:
+  explicit LookupData(P2PManager::LookupCallback callback)
+    : callback_(callback) {}
+
+  ~LookupData() {
+    if (timeout_task_ != MessageLoop::kTaskIdNull)
+      MessageLoop::current()->CancelTask(timeout_task_);
+    if (child_pid_)
+      Subprocess::Get().KillExec(child_pid_);
+  }
+
+  void InitiateLookup(const vector<string>& cmd, TimeDelta timeout) {
+    // NOTE: if we fail early (i.e. in this method), we need to schedule
+    // an idle to report the error. This is because we guarantee that
+    // the callback is always called from the message loop (this
+    // guarantee is useful for testing).
+
+    // We expect to run just "p2p-client" and find it in the path.
+    child_pid_ = Subprocess::Get().ExecFlags(
+        cmd, Subprocess::kSearchPath,
+        Bind(&LookupData::OnLookupDone, base::Unretained(this)));
+
+    if (!child_pid_) {
+      LOG(ERROR) << "Error spawning " << utils::StringVectorToString(cmd);
+      ReportErrorAndDeleteInIdle();
+      return;
+    }
+
+    if (timeout > TimeDelta()) {
+      timeout_task_ = MessageLoop::current()->PostDelayedTask(
+          FROM_HERE,
+          Bind(&LookupData::OnTimeout, base::Unretained(this)),
+          timeout);
+    }
+  }
+
+ private:
+  void ReportErrorAndDeleteInIdle() {
+    MessageLoop::current()->PostTask(FROM_HERE, Bind(
+        &LookupData::OnIdleForReportErrorAndDelete,
+        base::Unretained(this)));
+  }
+
+  void OnIdleForReportErrorAndDelete() {
+    ReportError();
+    delete this;
+  }
+
+  void IssueCallback(const string& url) {
+    if (!callback_.is_null())
+      callback_.Run(url);
+  }
+
+  void ReportError() {
+    if (reported_)
+      return;
+    IssueCallback("");
+    reported_ = true;
+  }
+
+  void ReportSuccess(const string& output) {
+    if (reported_)
+      return;
+    string url = output;
+    size_t newline_pos = url.find('\n');
+    if (newline_pos != string::npos)
+      url.resize(newline_pos);
+
+    // Since p2p-client(1) is constructing this URL itself strictly
+    // speaking there's no need to validate it... but, anyway, can't
+    // hurt.
+    if (url.compare(0, 7, "http://") == 0) {
+      IssueCallback(url);
+    } else {
+      LOG(ERROR) << "p2p URL '" << url << "' does not look right. Ignoring.";
+      ReportError();
+    }
+    reported_ = true;
+  }
+
+  void OnLookupDone(int return_code, const string& output) {
+    child_pid_ = 0;
+    if (return_code != 0) {
+      LOG(INFO) << "Child exited with non-zero exit code "
+                << return_code;
+      ReportError();
+    } else {
+      ReportSuccess(output);
+    }
+    delete this;
+  }
+
+  void OnTimeout() {
+    timeout_task_ = MessageLoop::kTaskIdNull;
+    ReportError();
+    delete this;
+  }
+
+  P2PManager::LookupCallback callback_;
+
+  // The Subprocess tag of the running process. A value of 0 means that the
+  // process is not running.
+  pid_t child_pid_{0};
+
+  // The timeout task_id we are waiting on, if any.
+  MessageLoop::TaskId timeout_task_{MessageLoop::kTaskIdNull};
+
+  bool reported_{false};
+};
+
+void P2PManagerImpl::LookupUrlForFile(const string& file_id,
+                                      size_t minimum_size,
+                                      TimeDelta max_time_to_wait,
+                                      LookupCallback callback) {
+  LookupData *lookup_data = new LookupData(callback);
+  string file_id_with_ext = file_id + "." + file_extension_;
+  vector<string> args = configuration_->GetP2PClientArgs(file_id_with_ext,
+                                                         minimum_size);
+  lookup_data->InitiateLookup(args, max_time_to_wait);
+}
+
+bool P2PManagerImpl::FileShare(const string& file_id,
+                               size_t expected_size) {
+  // Check if file already exist.
+  FilePath path = FileGetPath(file_id);
+  if (!path.empty()) {
+    // File exists - double check its expected size though.
+    ssize_t file_expected_size = FileGetExpectedSize(file_id);
+    if (file_expected_size == -1 ||
+        static_cast<size_t>(file_expected_size) != expected_size) {
+      LOG(ERROR) << "Existing p2p file " << path.value()
+                 << " with expected_size=" << file_expected_size
+                 << " does not match the passed in"
+                 << " expected_size=" << expected_size;
+      return false;
+    }
+    return true;
+  }
+
+  // Before creating the file, bail if statvfs(3) indicates that at
+  // least twice the size is not available in P2P_DIR.
+  struct statvfs statvfsbuf;
+  FilePath p2p_dir = configuration_->GetP2PDir();
+  if (statvfs(p2p_dir.value().c_str(), &statvfsbuf) != 0) {
+    PLOG(ERROR) << "Error calling statvfs() for dir " << p2p_dir.value();
+    return false;
+  }
+  size_t free_bytes =
+      static_cast<size_t>(statvfsbuf.f_bsize) * statvfsbuf.f_bavail;
+  if (free_bytes < 2 * expected_size) {
+    // This can easily happen and is worth reporting.
+    LOG(INFO) << "Refusing to allocate p2p file of " << expected_size
+              << " bytes since the directory " << p2p_dir.value()
+              << " only has " << free_bytes
+              << " bytes available and this is less than twice the"
+              << " requested size.";
+    return false;
+  }
+
+  // Okie-dokey looks like enough space is available - create the file.
+  path = GetPath(file_id, kNonVisible);
+  int fd = open(path.value().c_str(), O_CREAT | O_RDWR, 0644);
+  if (fd == -1) {
+    PLOG(ERROR) << "Error creating file with path " << path.value();
+    return false;
+  }
+  ScopedFdCloser fd_closer(&fd);
+
+  // If the final size is known, allocate the file (e.g. reserve disk
+  // space) and set the user.cros-p2p-filesize xattr.
+  if (expected_size != 0) {
+    if (fallocate(fd,
+                  FALLOC_FL_KEEP_SIZE,  // Keep file size as 0.
+                  0,
+                  expected_size) != 0) {
+      if (errno == ENOSYS || errno == EOPNOTSUPP) {
+        // If the filesystem doesn't support the fallocate, keep
+        // going. This is helpful when running unit tests on build
+        // machines with ancient filesystems and/or OSes.
+        PLOG(WARNING) << "Ignoring fallocate(2) failure";
+      } else {
+        // ENOSPC can happen (funky race though, cf. the statvfs() check
+        // above), handle it gracefully, e.g. use logging level INFO.
+        PLOG(INFO) << "Error allocating " << expected_size
+                   << " bytes for file " << path.value();
+        if (unlink(path.value().c_str()) != 0) {
+          PLOG(ERROR) << "Error deleting file with path " << path.value();
+        }
+        return false;
+      }
+    }
+
+    string decimal_size = std::to_string(expected_size);
+    if (fsetxattr(fd, kCrosP2PFileSizeXAttrName,
+                  decimal_size.c_str(), decimal_size.size(), 0) != 0) {
+      PLOG(ERROR) << "Error setting xattr " << path.value();
+      return false;
+    }
+  }
+
+  return true;
+}
+
+FilePath P2PManagerImpl::FileGetPath(const string& file_id) {
+  struct stat statbuf;
+  FilePath path;
+
+  path = GetPath(file_id, kVisible);
+  if (stat(path.value().c_str(), &statbuf) == 0) {
+    return path;
+  }
+
+  path = GetPath(file_id, kNonVisible);
+  if (stat(path.value().c_str(), &statbuf) == 0) {
+    return path;
+  }
+
+  path.clear();
+  return path;
+}
+
+bool P2PManagerImpl::FileGetVisible(const string& file_id,
+                                    bool *out_result) {
+  FilePath path = FileGetPath(file_id);
+  if (path.empty()) {
+    LOG(ERROR) << "No file for id " << file_id;
+    return false;
+  }
+  if (out_result != nullptr)
+    *out_result = path.MatchesExtension(kP2PExtension);
+  return true;
+}
+
+bool P2PManagerImpl::FileMakeVisible(const string& file_id) {
+  FilePath path = FileGetPath(file_id);
+  if (path.empty()) {
+    LOG(ERROR) << "No file for id " << file_id;
+    return false;
+  }
+
+  // Already visible?
+  if (path.MatchesExtension(kP2PExtension))
+    return true;
+
+  LOG_ASSERT(path.MatchesExtension(kTmpExtension));
+  FilePath new_path = path.RemoveExtension();
+  LOG_ASSERT(new_path.MatchesExtension(kP2PExtension));
+  if (rename(path.value().c_str(), new_path.value().c_str()) != 0) {
+    PLOG(ERROR) << "Error renaming " << path.value()
+                << " to " << new_path.value();
+    return false;
+  }
+
+  return true;
+}
+
+ssize_t P2PManagerImpl::FileGetSize(const string& file_id) {
+  FilePath path = FileGetPath(file_id);
+  if (path.empty())
+    return -1;
+
+  return utils::FileSize(path.value());
+}
+
+ssize_t P2PManagerImpl::FileGetExpectedSize(const string& file_id) {
+  FilePath path = FileGetPath(file_id);
+  if (path.empty())
+    return -1;
+
+  char ea_value[64] = { 0 };
+  ssize_t ea_size;
+  ea_size = getxattr(path.value().c_str(), kCrosP2PFileSizeXAttrName,
+                     &ea_value, sizeof(ea_value) - 1);
+  if (ea_size == -1) {
+    PLOG(ERROR) << "Error calling getxattr() on file " << path.value();
+    return -1;
+  }
+
+  char* endp = nullptr;
+  long long int val = strtoll(ea_value, &endp, 0);  // NOLINT(runtime/int)
+  if (*endp != '\0') {
+    LOG(ERROR) << "Error parsing the value '" << ea_value
+               << "' of the xattr " << kCrosP2PFileSizeXAttrName
+               << " as an integer";
+    return -1;
+  }
+
+  return val;
+}
+
+int P2PManagerImpl::CountSharedFiles() {
+  int num_files = 0;
+
+  FilePath p2p_dir = configuration_->GetP2PDir();
+  const string ext_visible = GetExt(kVisible);
+  const string ext_non_visible = GetExt(kNonVisible);
+
+  base::FileEnumerator dir(p2p_dir, false, base::FileEnumerator::FILES);
+  for (FilePath name = dir.Next(); !name.empty(); name = dir.Next()) {
+    if (base::EndsWith(name.value(), ext_visible, true) ||
+        base::EndsWith(name.value(), ext_non_visible, true))
+      num_files += 1;
+  }
+
+  return num_files;
+}
+
+void P2PManagerImpl::ScheduleEnabledStatusChange() {
+  if (waiting_for_enabled_status_change_)
+    return;
+
+  Callback<void(EvalStatus, const bool&)> callback = Bind(
+      &P2PManagerImpl::OnEnabledStatusChange, base::Unretained(this));
+  update_manager_->AsyncPolicyRequest(callback, &Policy::P2PEnabledChanged,
+                                      is_enabled_);
+  waiting_for_enabled_status_change_ = true;
+}
+
+void P2PManagerImpl::OnEnabledStatusChange(EvalStatus status,
+                                           const bool& result) {
+  waiting_for_enabled_status_change_ = false;
+
+  if (status == EvalStatus::kSucceeded) {
+    if (result == is_enabled_) {
+      LOG(WARNING) << "P2P enabled status did not change, which means that it "
+                      "is permanent; not scheduling further checks.";
+      waiting_for_enabled_status_change_ = true;
+      return;
+    }
+
+    is_enabled_ = result;
+
+    // If P2P is running but shouldn't be, make sure it isn't.
+    if (may_be_running_ && !is_enabled_ && !EnsureP2PNotRunning()) {
+      LOG(WARNING) << "Failed to stop P2P service.";
+    }
+  } else {
+    LOG(WARNING)
+        << "P2P enabled tracking failed (possibly timed out); retrying.";
+  }
+
+  ScheduleEnabledStatusChange();
+}
+
+P2PManager* P2PManager::Construct(
+    Configuration *configuration,
+    ClockInterface *clock,
+    UpdateManager* update_manager,
+    const string& file_extension,
+    const int num_files_to_keep,
+    const TimeDelta& max_file_age) {
+  return new P2PManagerImpl(configuration,
+                            clock,
+                            update_manager,
+                            file_extension,
+                            num_files_to_keep,
+                            max_file_age);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/p2p_manager.h b/p2p_manager.h
new file mode 100644
index 0000000..4ffab9a
--- /dev/null
+++ b/p2p_manager.h
@@ -0,0 +1,188 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_P2P_MANAGER_H_
+#define UPDATE_ENGINE_P2P_MANAGER_H_
+
+#include <string>
+#include <vector>
+
+#include <base/callback.h>
+#include <base/files/file_path.h>
+#include <base/memory/ref_counted.h>
+#include <base/time/time.h>
+#include <policy/device_policy.h>
+#include <policy/libpolicy.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/update_manager/update_manager.h"
+
+namespace chromeos_update_engine {
+
+// Interface for sharing and discovering files via p2p.
+class P2PManager {
+ public:
+  // Interface used for P2PManager implementations. The sole reason
+  // for this interface is unit testing.
+  class Configuration {
+   public:
+    virtual ~Configuration() {}
+
+    // Gets the path to the p2p dir being used, e.g. /var/cache/p2p.
+    virtual base::FilePath GetP2PDir() = 0;
+
+    // Gets the argument vector for starting (if |is_start| is True)
+    // resp. stopping (if |is_start| is False) the p2p service
+    // e.g. ["initctl", "start", "p2p"] or ["initctl", "stop", "p2p"].
+    virtual std::vector<std::string> GetInitctlArgs(bool is_start) = 0;
+
+    // Gets the argument vector for invoking p2p-client, e.g.
+    // "p2p-client --get-url=file_id_we_want --minimum-size=42123".
+    virtual std::vector<std::string> GetP2PClientArgs(
+        const std::string& file_id, size_t minimum_size) = 0;
+  };
+
+  virtual ~P2PManager() {}
+
+  // The type for the callback used in LookupUrlForFile().
+  // If the lookup failed, |url| is empty.
+  typedef base::Callback<void(const std::string& url)> LookupCallback;
+
+  // Use the device policy specified by |device_policy|. If this is
+  // null, then no device policy is used.
+  virtual void SetDevicePolicy(const policy::DevicePolicy* device_policy) = 0;
+
+  // Returns true iff P2P is currently allowed for use on this device. This
+  // value is determined and maintained by the Update Manager.
+  virtual bool IsP2PEnabled() = 0;
+
+  // Ensures that the p2p subsystem is running (e.g. starts it if it's
+  // not already running) and blocks until this is so. Returns false
+  // if an error occurred.
+  virtual bool EnsureP2PRunning() = 0;
+
+  // Ensures that the p2p subsystem is not running (e.g. stops it if
+  // it's running) and blocks until this is so. Returns false if an
+  // error occurred.
+  virtual bool EnsureP2PNotRunning() = 0;
+
+  // Cleans up files in /var/cache/p2p owned by this application as
+  // per the |file_extension| and |num_files_to_keep| values passed
+  // when the object was constructed. This may be called even if
+  // the p2p subsystem is not running.
+  virtual bool PerformHousekeeping() = 0;
+
+  // Asynchronously finds a peer that serves the file identified by
+  // |file_id|. If |minimum_size| is non-zero, will find a peer that
+  // has at least that many bytes. When the result is ready |callback|
+  // is called from the current message loop.
+  //
+  // This operation may take a very long time to complete because part
+  // of the p2p protocol involves waiting for the LAN-wide sum of all
+  // num-connections to drop below a given threshold. However, if
+  // |max_time_to_wait| is non-zero, the operation is guaranteed to
+  // not exceed this duration.
+  //
+  // If the file is not available on the LAN (or if mDNS/DNS-SD is
+  // filtered), this is guaranteed to not take longer than 5 seconds.
+  virtual void LookupUrlForFile(const std::string& file_id,
+                                size_t minimum_size,
+                                base::TimeDelta max_time_to_wait,
+                                LookupCallback callback) = 0;
+
+  // Shares a file identified by |file_id| in the directory
+  // /var/cache/p2p. Initially the file will not be visible, that is,
+  // it will have a .tmp extension and not be shared via p2p. Use the
+  // FileMakeVisible() method to change this.
+  //
+  // If you know the final size of the file, pass it in the
+  // |expected_size| parameter. Otherwise pass zero. If non-zero, the
+  // amount of free space in /var/cache/p2p is checked and if there is
+  // less than twice the amount of space available, this method
+  // fails. Additionally, disk space will be reserved via fallocate(2)
+  // and |expected_size| is written to the user.cros-p2p-filesize
+  // xattr of the created file.
+  //
+  // If the file already exists, true is returned. Any on-disk xattr
+  // is not updated.
+  virtual bool FileShare(const std::string& file_id,
+                         size_t expected_size) = 0;
+
+  // Gets a fully qualified path for the file identified by |file_id|.
+  // If the file has not been shared already using the FileShare()
+  // method, an empty base::FilePath is returned - use FilePath::empty() to
+  // find out.
+  virtual base::FilePath FileGetPath(const std::string& file_id) = 0;
+
+  // Gets the actual size of the file identified by |file_id|. This is
+  // equivalent to reading the value of the st_size field of the
+  // struct stat on the file given by FileGetPath(). Returns -1 if an
+  // error occurs.
+  //
+  // For a file just created with FileShare() this will return 0.
+  virtual ssize_t FileGetSize(const std::string& file_id) = 0;
+
+  // Gets the expected size of the file identified by |file_id|. This
+  // is equivalent to reading the value of the user.cros-p2p-filesize
+  // xattr on the file given by FileGetPath(). Returns -1 if an error
+  // occurs.
+  //
+  // For a file just created with FileShare() this will return the
+  // value of the |expected_size| parameter passed to that method.
+  virtual ssize_t FileGetExpectedSize(const std::string& file_id) = 0;
+
+  // Gets whether the file identified by |file_id| is publicly
+  // visible. If |out_result| is not null, the result is returned
+  // there. Returns false if an error occurs.
+  virtual bool FileGetVisible(const std::string& file_id,
+                              bool *out_result) = 0;
+
+  // Makes the file identified by |file_id| publicly visible
+  // (e.g. removes the .tmp extension). If the file is already
+  // visible, this method does nothing. Returns False if
+  // the method fails or there is no file for |file_id|.
+  virtual bool FileMakeVisible(const std::string& file_id) = 0;
+
+  // Counts the number of shared files used by this application
+  // (cf. the |file_extension parameter|. Returns -1 if an error
+  // occurred.
+  virtual int CountSharedFiles() = 0;
+
+  // Creates a suitable P2PManager instance and initializes the object
+  // so it's ready for use. The |file_extension| parameter is used to
+  // identify your application, use e.g. "cros_au".  If
+  // |configuration| is non-null, the P2PManager will take ownership
+  // of the Configuration object and use it (hence, it must be
+  // heap-allocated).
+  //
+  // The |num_files_to_keep| parameter specifies how many files to
+  // keep after performing housekeeping (cf. the PerformHousekeeping()
+  // method) - pass zero to allow infinitely many files. The
+  // |max_file_age| parameter specifies the maximum file age after
+  // performing housekeeping (pass zero to allow files of any age).
+  static P2PManager* Construct(
+      Configuration *configuration,
+      ClockInterface *clock,
+      chromeos_update_manager::UpdateManager* update_manager,
+      const std::string& file_extension,
+      const int num_files_to_keep,
+      const base::TimeDelta& max_file_age);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_P2P_MANAGER_H_
diff --git a/p2p_manager_unittest.cc b/p2p_manager_unittest.cc
new file mode 100644
index 0000000..463c0e2
--- /dev/null
+++ b/p2p_manager_unittest.cc
@@ -0,0 +1,515 @@
+//
+// Copyright (C) 2012 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 "update_engine/p2p_manager.h"
+
+#include <dirent.h>
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <sys/xattr.h>
+#include <unistd.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/files/file_util.h>
+#include <base/message_loop/message_loop.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/asynchronous_signal_handler.h>
+#include <brillo/message_loops/base_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <policy/libpolicy.h>
+#include <policy/mock_device_policy.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_p2p_manager_configuration.h"
+#include "update_engine/update_manager/fake_update_manager.h"
+#include "update_engine/update_manager/mock_policy.h"
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+using testing::DoAll;
+using testing::Return;
+using testing::SetArgPointee;
+using testing::_;
+
+namespace chromeos_update_engine {
+
+// Test fixture that sets up a testing configuration (with e.g. a
+// temporary p2p dir) for P2PManager and cleans up when the test is
+// done.
+class P2PManagerTest : public testing::Test {
+ protected:
+  P2PManagerTest() : fake_um_(&fake_clock_) {}
+  ~P2PManagerTest() override {}
+
+  // Derived from testing::Test.
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    async_signal_handler_.Init();
+    subprocess_.Init(&async_signal_handler_);
+    test_conf_ = new FakeP2PManagerConfiguration();
+
+    // Allocate and install a mock policy implementation in the fake Update
+    // Manager.  Note that the FakeUpdateManager takes ownership of the policy
+    // object.
+    mock_policy_ = new chromeos_update_manager::MockPolicy(&fake_clock_);
+    fake_um_.set_policy(mock_policy_);
+
+    // Construct the P2P manager under test.
+    manager_.reset(P2PManager::Construct(test_conf_, &fake_clock_, &fake_um_,
+                                         "cros_au", 3,
+                                         TimeDelta::FromDays(5)));
+  }
+
+  base::MessageLoopForIO base_loop_;
+  brillo::BaseMessageLoop loop_{&base_loop_};
+  brillo::AsynchronousSignalHandler async_signal_handler_;
+  Subprocess subprocess_;
+
+  // The P2PManager::Configuration instance used for testing.
+  FakeP2PManagerConfiguration *test_conf_;
+
+  FakeClock fake_clock_;
+  chromeos_update_manager::MockPolicy *mock_policy_ = nullptr;
+  chromeos_update_manager::FakeUpdateManager fake_um_;
+
+  unique_ptr<P2PManager> manager_;
+};
+
+
+// Check that IsP2PEnabled() polls the policy correctly, with the value not
+// changing between calls.
+TEST_F(P2PManagerTest, P2PEnabledInitAndNotChanged) {
+  EXPECT_CALL(*mock_policy_, P2PEnabled(_, _, _, _));
+  EXPECT_CALL(*mock_policy_, P2PEnabledChanged(_, _, _, _, false));
+
+  EXPECT_FALSE(manager_->IsP2PEnabled());
+  brillo::MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_FALSE(manager_->IsP2PEnabled());
+}
+
+// Check that IsP2PEnabled() polls the policy correctly, with the value changing
+// between calls.
+TEST_F(P2PManagerTest, P2PEnabledInitAndChanged) {
+  EXPECT_CALL(*mock_policy_, P2PEnabled(_, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<3>(true),
+              Return(chromeos_update_manager::EvalStatus::kSucceeded)));
+  EXPECT_CALL(*mock_policy_, P2PEnabledChanged(_, _, _, _, true));
+  EXPECT_CALL(*mock_policy_, P2PEnabledChanged(_, _, _, _, false));
+
+  EXPECT_TRUE(manager_->IsP2PEnabled());
+  brillo::MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_FALSE(manager_->IsP2PEnabled());
+}
+
+// Check that we keep the $N newest files with the .$EXT.p2p extension.
+TEST_F(P2PManagerTest, HousekeepingCountLimit) {
+  // Specifically pass 0 for |max_file_age| to allow files of any age. Note that
+  // we need to reallocate the test_conf_ member, whose currently aliased object
+  // will be freed.
+  test_conf_ = new FakeP2PManagerConfiguration();
+  manager_.reset(P2PManager::Construct(
+      test_conf_, &fake_clock_, &fake_um_, "cros_au", 3,
+      TimeDelta() /* max_file_age */));
+  EXPECT_EQ(manager_->CountSharedFiles(), 0);
+
+  base::Time start_time = base::Time::FromDoubleT(1246996800.);
+  // Generate files with different timestamps matching our pattern and generate
+  // other files not matching the pattern.
+  for (int n = 0; n < 5; n++) {
+    base::FilePath path = test_conf_->GetP2PDir().Append(base::StringPrintf(
+        "file_%d.cros_au.p2p", n));
+    base::Time file_time = start_time + TimeDelta::FromMinutes(n);
+    EXPECT_EQ(0, base::WriteFile(path, nullptr, 0));
+    EXPECT_TRUE(base::TouchFile(path, file_time, file_time));
+
+    path = test_conf_->GetP2PDir().Append(base::StringPrintf(
+        "file_%d.OTHER.p2p", n));
+    EXPECT_EQ(0, base::WriteFile(path, nullptr, 0));
+    EXPECT_TRUE(base::TouchFile(path, file_time, file_time));
+  }
+  // CountSharedFiles() only counts 'cros_au' files.
+  EXPECT_EQ(manager_->CountSharedFiles(), 5);
+
+  EXPECT_TRUE(manager_->PerformHousekeeping());
+
+  // At this point - after HouseKeeping - we should only have
+  // eight files left.
+  for (int n = 0; n < 5; n++) {
+    string file_name;
+    bool expect;
+
+    expect = (n >= 2);
+    file_name = base::StringPrintf(
+        "%s/file_%d.cros_au.p2p",
+         test_conf_->GetP2PDir().value().c_str(), n);
+    EXPECT_EQ(expect, utils::FileExists(file_name.c_str()));
+
+    file_name = base::StringPrintf(
+        "%s/file_%d.OTHER.p2p",
+        test_conf_->GetP2PDir().value().c_str(), n);
+    EXPECT_TRUE(utils::FileExists(file_name.c_str()));
+  }
+  // CountSharedFiles() only counts 'cros_au' files.
+  EXPECT_EQ(manager_->CountSharedFiles(), 3);
+}
+
+// Check that we keep files with the .$EXT.p2p extension not older
+// than some specificed age (5 days, in this test).
+TEST_F(P2PManagerTest, HousekeepingAgeLimit) {
+  // We set the cutoff time to be 1 billion seconds (01:46:40 UTC on 9
+  // September 2001 - arbitrary number, but constant to avoid test
+  // flakiness) since the epoch and then we put two files before that
+  // date and three files after.
+  base::Time cutoff_time = base::Time::FromTimeT(1000000000);
+  TimeDelta age_limit = TimeDelta::FromDays(5);
+
+  // Set the clock just so files with a timestamp before |cutoff_time|
+  // will be deleted at housekeeping.
+  fake_clock_.SetWallclockTime(cutoff_time + age_limit);
+
+  // Specifically pass 0 for |num_files_to_keep| to allow any number of files.
+  // Note that we need to reallocate the test_conf_ member, whose currently
+  // aliased object will be freed.
+  test_conf_ = new FakeP2PManagerConfiguration();
+  manager_.reset(P2PManager::Construct(
+      test_conf_, &fake_clock_, &fake_um_, "cros_au",
+      0 /* num_files_to_keep */, age_limit));
+  EXPECT_EQ(manager_->CountSharedFiles(), 0);
+
+  // Generate files with different timestamps matching our pattern and generate
+  // other files not matching the pattern.
+  for (int n = 0; n < 5; n++) {
+    base::FilePath path = test_conf_->GetP2PDir().Append(base::StringPrintf(
+        "file_%d.cros_au.p2p", n));
+
+    // With five files and aiming for two of them to be before
+    // |cutoff_time|, we distribute it like this:
+    //
+    //  -------- 0 -------- 1 -------- 2 -------- 3 -------- 4 --------
+    //                            |
+    //                       cutoff_time
+    //
+    base::Time file_date = cutoff_time + (n - 2) * TimeDelta::FromDays(1)
+        + TimeDelta::FromHours(12);
+
+    EXPECT_EQ(0, base::WriteFile(path, nullptr, 0));
+    EXPECT_TRUE(base::TouchFile(path, file_date, file_date));
+
+    path = test_conf_->GetP2PDir().Append(base::StringPrintf(
+        "file_%d.OTHER.p2p", n));
+    EXPECT_EQ(0, base::WriteFile(path, nullptr, 0));
+    EXPECT_TRUE(base::TouchFile(path, file_date, file_date));
+  }
+  // CountSharedFiles() only counts 'cros_au' files.
+  EXPECT_EQ(manager_->CountSharedFiles(), 5);
+
+  EXPECT_TRUE(manager_->PerformHousekeeping());
+
+  // At this point - after HouseKeeping - we should only have
+  // eight files left.
+  for (int n = 0; n < 5; n++) {
+    string file_name;
+    bool expect;
+
+    expect = (n >= 2);
+    file_name = base::StringPrintf(
+        "%s/file_%d.cros_au.p2p",
+         test_conf_->GetP2PDir().value().c_str(), n);
+    EXPECT_EQ(expect, utils::FileExists(file_name.c_str()));
+
+    file_name = base::StringPrintf(
+        "%s/file_%d.OTHER.p2p",
+        test_conf_->GetP2PDir().value().c_str(), n);
+    EXPECT_TRUE(utils::FileExists(file_name.c_str()));
+  }
+  // CountSharedFiles() only counts 'cros_au' files.
+  EXPECT_EQ(manager_->CountSharedFiles(), 3);
+}
+
+static bool CheckP2PFile(const string& p2p_dir, const string& file_name,
+                         ssize_t expected_size, ssize_t expected_size_xattr) {
+  string path = p2p_dir + "/" + file_name;
+  char ea_value[64] = { 0 };
+  ssize_t ea_size;
+
+  off_t p2p_size = utils::FileSize(path);
+  if (p2p_size < 0) {
+    LOG(ERROR) << "File " << path << " does not exist";
+    return false;
+  }
+
+  if (expected_size != 0) {
+    if (p2p_size != expected_size) {
+      LOG(ERROR) << "Expected size " << expected_size
+                 << " but size was " << p2p_size;
+      return false;
+    }
+  }
+
+  if (expected_size_xattr == 0) {
+    ea_size = getxattr(path.c_str(), "user.cros-p2p-filesize",
+                       &ea_value, sizeof ea_value - 1);
+    if (ea_size == -1 && errno == ENODATA) {
+      // This is valid behavior as we support files without the xattr set.
+    } else {
+      PLOG(ERROR) << "getxattr() didn't fail with ENODATA as expected, "
+                  << "ea_size=" << ea_size << ", errno=" << errno;
+      return false;
+    }
+  } else {
+    ea_size = getxattr(path.c_str(), "user.cros-p2p-filesize",
+                       &ea_value, sizeof ea_value - 1);
+    if (ea_size < 0) {
+      LOG(ERROR) << "Error getting xattr attribute";
+      return false;
+    }
+    char* endp = nullptr;
+    long long int val = strtoll(ea_value, &endp, 0);  // NOLINT(runtime/int)
+    if (endp == nullptr || *endp != '\0') {
+      LOG(ERROR) << "Error parsing xattr '" << ea_value
+                 << "' as an integer";
+      return false;
+    }
+    if (val != expected_size_xattr) {
+      LOG(ERROR) << "Expected xattr size " << expected_size_xattr
+                 << " but size was " << val;
+      return false;
+    }
+  }
+
+  return true;
+}
+
+static bool CreateP2PFile(string p2p_dir, string file_name,
+                          size_t size, size_t size_xattr) {
+  string path = p2p_dir + "/" + file_name;
+
+  int fd = open(path.c_str(), O_CREAT|O_RDWR, 0644);
+  if (fd == -1) {
+    PLOG(ERROR) << "Error creating file with path " << path;
+    return false;
+  }
+  if (ftruncate(fd, size) != 0) {
+    PLOG(ERROR) << "Error truncating " << path << " to size " << size;
+    close(fd);
+    return false;
+  }
+
+  if (size_xattr != 0) {
+    string decimal_size = std::to_string(size_xattr);
+    if (fsetxattr(fd, "user.cros-p2p-filesize",
+                  decimal_size.c_str(), decimal_size.size(), 0) != 0) {
+      PLOG(ERROR) << "Error setting xattr on " << path;
+      close(fd);
+      return false;
+    }
+  }
+
+  close(fd);
+  return true;
+}
+
+// Check that sharing a *new* file works.
+TEST_F(P2PManagerTest, ShareFile) {
+  if (!test_utils::IsXAttrSupported(base::FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+  const int kP2PTestFileSize = 1000 * 1000;  // 1 MB
+
+  EXPECT_TRUE(manager_->FileShare("foo", kP2PTestFileSize));
+  EXPECT_EQ(manager_->FileGetPath("foo"),
+            test_conf_->GetP2PDir().Append("foo.cros_au.p2p.tmp"));
+  EXPECT_TRUE(CheckP2PFile(test_conf_->GetP2PDir().value(),
+                           "foo.cros_au.p2p.tmp", 0, kP2PTestFileSize));
+
+  // Sharing it again - with the same expected size - should return true
+  EXPECT_TRUE(manager_->FileShare("foo", kP2PTestFileSize));
+
+  // ... but if we use the wrong size, it should fail
+  EXPECT_FALSE(manager_->FileShare("foo", kP2PTestFileSize + 1));
+}
+
+// Check that making a shared file visible, does what is expected.
+TEST_F(P2PManagerTest, MakeFileVisible) {
+  if (!test_utils::IsXAttrSupported(base::FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+  const int kP2PTestFileSize = 1000 * 1000;  // 1 MB
+
+  // First, check that it's not visible.
+  manager_->FileShare("foo", kP2PTestFileSize);
+  EXPECT_EQ(manager_->FileGetPath("foo"),
+            test_conf_->GetP2PDir().Append("foo.cros_au.p2p.tmp"));
+  EXPECT_TRUE(CheckP2PFile(test_conf_->GetP2PDir().value(),
+                           "foo.cros_au.p2p.tmp", 0, kP2PTestFileSize));
+  // Make the file visible and check that it changed its name. Do it
+  // twice to check that FileMakeVisible() is idempotent.
+  for (int n = 0; n < 2; n++) {
+    manager_->FileMakeVisible("foo");
+    EXPECT_EQ(manager_->FileGetPath("foo"),
+              test_conf_->GetP2PDir().Append("foo.cros_au.p2p"));
+    EXPECT_TRUE(CheckP2PFile(test_conf_->GetP2PDir().value(),
+                             "foo.cros_au.p2p", 0, kP2PTestFileSize));
+  }
+}
+
+// Check that we return the right values for existing files in P2P_DIR.
+TEST_F(P2PManagerTest, ExistingFiles) {
+  if (!test_utils::IsXAttrSupported(base::FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+
+  bool visible;
+
+  // Check that errors are returned if the file does not exist
+  EXPECT_EQ(manager_->FileGetPath("foo"), base::FilePath());
+  EXPECT_EQ(manager_->FileGetSize("foo"), -1);
+  EXPECT_EQ(manager_->FileGetExpectedSize("foo"), -1);
+  EXPECT_FALSE(manager_->FileGetVisible("foo", nullptr));
+  // ... then create the file ...
+  EXPECT_TRUE(CreateP2PFile(test_conf_->GetP2PDir().value(),
+                            "foo.cros_au.p2p", 42, 43));
+  // ... and then check that the expected values are returned
+  EXPECT_EQ(manager_->FileGetPath("foo"),
+            test_conf_->GetP2PDir().Append("foo.cros_au.p2p"));
+  EXPECT_EQ(manager_->FileGetSize("foo"), 42);
+  EXPECT_EQ(manager_->FileGetExpectedSize("foo"), 43);
+  EXPECT_TRUE(manager_->FileGetVisible("foo", &visible));
+  EXPECT_TRUE(visible);
+
+  // One more time, this time with a .tmp variant. First ensure it errors out..
+  EXPECT_EQ(manager_->FileGetPath("bar"), base::FilePath());
+  EXPECT_EQ(manager_->FileGetSize("bar"), -1);
+  EXPECT_EQ(manager_->FileGetExpectedSize("bar"), -1);
+  EXPECT_FALSE(manager_->FileGetVisible("bar", nullptr));
+  // ... then create the file ...
+  EXPECT_TRUE(CreateP2PFile(test_conf_->GetP2PDir().value(),
+                            "bar.cros_au.p2p.tmp", 44, 45));
+  // ... and then check that the expected values are returned
+  EXPECT_EQ(manager_->FileGetPath("bar"),
+            test_conf_->GetP2PDir().Append("bar.cros_au.p2p.tmp"));
+  EXPECT_EQ(manager_->FileGetSize("bar"), 44);
+  EXPECT_EQ(manager_->FileGetExpectedSize("bar"), 45);
+  EXPECT_TRUE(manager_->FileGetVisible("bar", &visible));
+  EXPECT_FALSE(visible);
+}
+
+// This is a little bit ugly but short of mocking a 'p2p' service this
+// will have to do. E.g. we essentially simulate the various
+// behaviours of initctl(8) that we rely on.
+TEST_F(P2PManagerTest, StartP2P) {
+  // Check that we can start the service
+  test_conf_->SetInitctlStartCommand({"true"});
+  EXPECT_TRUE(manager_->EnsureP2PRunning());
+  test_conf_->SetInitctlStartCommand({"false"});
+  EXPECT_FALSE(manager_->EnsureP2PRunning());
+  test_conf_->SetInitctlStartCommand({
+      "sh", "-c", "echo \"initctl: Job is already running: p2p\" >&2; false"});
+  EXPECT_TRUE(manager_->EnsureP2PRunning());
+  test_conf_->SetInitctlStartCommand({
+      "sh", "-c", "echo something else >&2; false"});
+  EXPECT_FALSE(manager_->EnsureP2PRunning());
+}
+
+// Same comment as for StartP2P
+TEST_F(P2PManagerTest, StopP2P) {
+  // Check that we can start the service
+  test_conf_->SetInitctlStopCommand({"true"});
+  EXPECT_TRUE(manager_->EnsureP2PNotRunning());
+  test_conf_->SetInitctlStopCommand({"false"});
+  EXPECT_FALSE(manager_->EnsureP2PNotRunning());
+  test_conf_->SetInitctlStopCommand({
+      "sh", "-c", "echo \"initctl: Unknown instance \" >&2; false"});
+  EXPECT_TRUE(manager_->EnsureP2PNotRunning());
+  test_conf_->SetInitctlStopCommand({
+      "sh", "-c", "echo something else >&2; false"});
+  EXPECT_FALSE(manager_->EnsureP2PNotRunning());
+}
+
+static void ExpectUrl(const string& expected_url,
+                      const string& url) {
+  EXPECT_EQ(url, expected_url);
+  MessageLoop::current()->BreakLoop();
+}
+
+// Like StartP2P, we're mocking the different results that p2p-client
+// can return. It's not pretty but it works.
+TEST_F(P2PManagerTest, LookupURL) {
+  // Emulate p2p-client returning valid URL with "fooX", 42 and "cros_au"
+  // being propagated in the right places.
+  test_conf_->SetP2PClientCommand({
+      "echo", "http://1.2.3.4/{file_id}_{minsize}"});
+  manager_->LookupUrlForFile("fooX", 42, TimeDelta(),
+                             base::Bind(ExpectUrl,
+                                        "http://1.2.3.4/fooX.cros_au_42"));
+  loop_.Run();
+
+  // Emulate p2p-client returning invalid URL.
+  test_conf_->SetP2PClientCommand({"echo", "not_a_valid_url"});
+  manager_->LookupUrlForFile("foobar", 42, TimeDelta(),
+                             base::Bind(ExpectUrl, ""));
+  loop_.Run();
+
+  // Emulate p2p-client conveying failure.
+  test_conf_->SetP2PClientCommand({"false"});
+  manager_->LookupUrlForFile("foobar", 42, TimeDelta(),
+                             base::Bind(ExpectUrl, ""));
+  loop_.Run();
+
+  // Emulate p2p-client not existing.
+  test_conf_->SetP2PClientCommand({"/path/to/non/existent/helper/program"});
+  manager_->LookupUrlForFile("foobar", 42,
+                             TimeDelta(),
+                             base::Bind(ExpectUrl, ""));
+  loop_.Run();
+
+  // Emulate p2p-client crashing.
+  test_conf_->SetP2PClientCommand({"sh", "-c", "kill -SEGV $$"});
+  manager_->LookupUrlForFile("foobar", 42, TimeDelta(),
+                             base::Bind(ExpectUrl, ""));
+  loop_.Run();
+
+  // Emulate p2p-client exceeding its timeout.
+  test_conf_->SetP2PClientCommand({
+      "sh", "-c", "echo http://1.2.3.4/; sleep 2"});
+  manager_->LookupUrlForFile("foobar", 42, TimeDelta::FromMilliseconds(500),
+                             base::Bind(ExpectUrl, ""));
+  loop_.Run();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/bzip_extent_writer.cc b/payload_consumer/bzip_extent_writer.cc
new file mode 100644
index 0000000..0fcc8ba
--- /dev/null
+++ b/payload_consumer/bzip_extent_writer.cc
@@ -0,0 +1,91 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/bzip_extent_writer.h"
+
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+const brillo::Blob::size_type kOutputBufferLength = 16 * 1024;
+}
+
+bool BzipExtentWriter::Init(FileDescriptorPtr fd,
+                            const vector<Extent>& extents,
+                            uint32_t block_size) {
+  // Init bzip2 stream
+  int rc = BZ2_bzDecompressInit(&stream_,
+                                0,   // verbosity. (0 == silent)
+                                0);  // 0 = faster algo, more memory
+
+  TEST_AND_RETURN_FALSE(rc == BZ_OK);
+
+  return next_->Init(fd, extents, block_size);
+}
+
+bool BzipExtentWriter::Write(const void* bytes, size_t count) {
+  brillo::Blob output_buffer(kOutputBufferLength);
+
+  // Copy the input data into |input_buffer_| only if |input_buffer_| already
+  // contains unconsumed data. Otherwise, process the data directly from the
+  // source.
+  const uint8_t* input = reinterpret_cast<const uint8_t*>(bytes);
+  const uint8_t* input_end = input + count;
+  if (!input_buffer_.empty()) {
+    input_buffer_.insert(input_buffer_.end(), input, input_end);
+    input = input_buffer_.data();
+    input_end = input + input_buffer_.size();
+  }
+  stream_.next_in = reinterpret_cast<char*>(const_cast<uint8_t*>(input));
+  stream_.avail_in = input_end - input;
+
+  for (;;) {
+    stream_.next_out = reinterpret_cast<char*>(output_buffer.data());
+    stream_.avail_out = output_buffer.size();
+
+    int rc = BZ2_bzDecompress(&stream_);
+    TEST_AND_RETURN_FALSE(rc == BZ_OK || rc == BZ_STREAM_END);
+
+    if (stream_.avail_out == output_buffer.size())
+      break;  // got no new bytes
+
+    TEST_AND_RETURN_FALSE(
+        next_->Write(output_buffer.data(),
+                     output_buffer.size() - stream_.avail_out));
+
+    if (rc == BZ_STREAM_END)
+      CHECK_EQ(stream_.avail_in, 0u);
+    if (stream_.avail_in == 0)
+      break;  // no more input to process
+  }
+
+  // Store unconsumed data (if any) in |input_buffer_|.
+  if (stream_.avail_in || !input_buffer_.empty()) {
+    brillo::Blob new_input_buffer(input_end - stream_.avail_in, input_end);
+    new_input_buffer.swap(input_buffer_);
+  }
+
+  return true;
+}
+
+bool BzipExtentWriter::EndImpl() {
+  TEST_AND_RETURN_FALSE(input_buffer_.empty());
+  TEST_AND_RETURN_FALSE(BZ2_bzDecompressEnd(&stream_) == BZ_OK);
+  return next_->End();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/bzip_extent_writer.h b/payload_consumer/bzip_extent_writer.h
new file mode 100644
index 0000000..0ad542e
--- /dev/null
+++ b/payload_consumer/bzip_extent_writer.h
@@ -0,0 +1,57 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_BZIP_EXTENT_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_BZIP_EXTENT_WRITER_H_
+
+#include <bzlib.h>
+#include <memory>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/extent_writer.h"
+
+// BzipExtentWriter is a concrete ExtentWriter subclass that bzip-decompresses
+// what it's given in Write. It passes the decompressed data to an underlying
+// ExtentWriter.
+
+namespace chromeos_update_engine {
+
+class BzipExtentWriter : public ExtentWriter {
+ public:
+  explicit BzipExtentWriter(std::unique_ptr<ExtentWriter> next)
+      : next_(std::move(next)) {
+    memset(&stream_, 0, sizeof(stream_));
+  }
+  ~BzipExtentWriter() override = default;
+
+  bool Init(FileDescriptorPtr fd,
+            const std::vector<Extent>& extents,
+            uint32_t block_size) override;
+  bool Write(const void* bytes, size_t count) override;
+  bool EndImpl() override;
+
+ private:
+  std::unique_ptr<ExtentWriter> next_;  // The underlying ExtentWriter.
+  bz_stream stream_;  // the libbz2 stream
+  brillo::Blob input_buffer_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_BZIP_EXTENT_WRITER_H_
diff --git a/payload_consumer/bzip_extent_writer_unittest.cc b/payload_consumer/bzip_extent_writer_unittest.cc
new file mode 100644
index 0000000..a52a286
--- /dev/null
+++ b/payload_consumer/bzip_extent_writer_unittest.cc
@@ -0,0 +1,145 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/bzip_extent_writer.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <brillo/make_unique_ptr.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using std::min;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+const char kPathTemplate[] = "./BzipExtentWriterTest-file.XXXXXX";
+const uint32_t kBlockSize = 4096;
+}
+
+class BzipExtentWriterTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    memcpy(path_, kPathTemplate, sizeof(kPathTemplate));
+    fd_.reset(new EintrSafeFileDescriptor);
+    int fd = mkstemp(path_);
+    ASSERT_TRUE(fd_->Open(path_, O_RDWR, 0600));
+    close(fd);
+  }
+  void TearDown() override {
+    fd_->Close();
+    unlink(path_);
+  }
+  void WriteAlignedExtents(size_t chunk_size, size_t first_chunk_size);
+  void TestZeroPad(bool aligned_size);
+
+  FileDescriptorPtr fd_;
+  char path_[sizeof(kPathTemplate)];
+};
+
+TEST_F(BzipExtentWriterTest, SimpleTest) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(0);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+
+  // 'echo test | bzip2 | hexdump' yields:
+  static const char test_uncompressed[] = "test\n";
+  static const uint8_t test[] = {
+    0x42, 0x5a, 0x68, 0x39, 0x31, 0x41, 0x59, 0x26, 0x53, 0x59, 0xcc, 0xc3,
+    0x71, 0xd4, 0x00, 0x00, 0x02, 0x41, 0x80, 0x00, 0x10, 0x02, 0x00, 0x0c,
+    0x00, 0x20, 0x00, 0x21, 0x9a, 0x68, 0x33, 0x4d, 0x19, 0x97, 0x8b, 0xb9,
+    0x22, 0x9c, 0x28, 0x48, 0x66, 0x61, 0xb8, 0xea, 0x00,
+  };
+
+  BzipExtentWriter bzip_writer(
+      brillo::make_unique_ptr(new DirectExtentWriter()));
+  EXPECT_TRUE(bzip_writer.Init(fd_, extents, kBlockSize));
+  EXPECT_TRUE(bzip_writer.Write(test, sizeof(test)));
+  EXPECT_TRUE(bzip_writer.End());
+
+  brillo::Blob buf;
+  EXPECT_TRUE(utils::ReadFile(path_, &buf));
+  EXPECT_EQ(strlen(test_uncompressed), buf.size());
+  EXPECT_EQ(string(buf.begin(), buf.end()), string(test_uncompressed));
+}
+
+TEST_F(BzipExtentWriterTest, ChunkedTest) {
+  const brillo::Blob::size_type kDecompressedLength = 2048 * 1024;  // 2 MiB
+  string decompressed_path;
+  ASSERT_TRUE(utils::MakeTempFile("BzipExtentWriterTest-decompressed-XXXXXX",
+                                  &decompressed_path, nullptr));
+  string compressed_path;
+  ASSERT_TRUE(utils::MakeTempFile("BzipExtentWriterTest-compressed-XXXXXX",
+                                  &compressed_path, nullptr));
+  const size_t kChunkSize = 3;
+
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(0);
+  extent.set_num_blocks(kDecompressedLength / kBlockSize + 1);
+  extents.push_back(extent);
+
+  brillo::Blob decompressed_data(kDecompressedLength);
+  test_utils::FillWithData(&decompressed_data);
+
+  EXPECT_TRUE(test_utils::WriteFileVector(
+      decompressed_path, decompressed_data));
+
+  EXPECT_EQ(0, test_utils::System(
+      string("cat ") + decompressed_path + "|bzip2>" + compressed_path));
+
+  brillo::Blob compressed_data;
+  EXPECT_TRUE(utils::ReadFile(compressed_path, &compressed_data));
+
+  BzipExtentWriter bzip_writer(
+      brillo::make_unique_ptr(new DirectExtentWriter()));
+  EXPECT_TRUE(bzip_writer.Init(fd_, extents, kBlockSize));
+
+  brillo::Blob original_compressed_data = compressed_data;
+  for (brillo::Blob::size_type i = 0; i < compressed_data.size();
+       i += kChunkSize) {
+    size_t this_chunk_size = min(kChunkSize, compressed_data.size() - i);
+    EXPECT_TRUE(bzip_writer.Write(&compressed_data[i], this_chunk_size));
+  }
+  EXPECT_TRUE(bzip_writer.End());
+
+  // Check that the const input has not been clobbered.
+  test_utils::ExpectVectorsEq(original_compressed_data, compressed_data);
+
+  brillo::Blob output;
+  EXPECT_TRUE(utils::ReadFile(path_, &output));
+  EXPECT_EQ(kDecompressedLength, output.size());
+  test_utils::ExpectVectorsEq(decompressed_data, output);
+
+  unlink(decompressed_path.c_str());
+  unlink(compressed_path.c_str());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/delta_performer.cc b/payload_consumer/delta_performer.cc
new file mode 100644
index 0000000..6261cb1
--- /dev/null
+++ b/payload_consumer/delta_performer.cc
@@ -0,0 +1,1794 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/delta_performer.h"
+
+#include <endian.h>
+#include <errno.h>
+#include <linux/fs.h>
+
+#include <algorithm>
+#include <cstring>
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/format_macros.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/data_encoding.h>
+#include <brillo/make_unique_ptr.h>
+#include <google/protobuf/repeated_field.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/terminator.h"
+#include "update_engine/payload_consumer/bzip_extent_writer.h"
+#include "update_engine/payload_consumer/download_action.h"
+#include "update_engine/payload_consumer/extent_writer.h"
+#if USE_MTD
+#include "update_engine/payload_consumer/mtd_file_descriptor.h"
+#endif
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_consumer/payload_verifier.h"
+#include "update_engine/payload_consumer/xz_extent_writer.h"
+
+using google::protobuf::RepeatedPtrField;
+using std::min;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+const uint64_t DeltaPerformer::kDeltaVersionOffset = sizeof(kDeltaMagic);
+const uint64_t DeltaPerformer::kDeltaVersionSize = 8;
+const uint64_t DeltaPerformer::kDeltaManifestSizeOffset =
+    kDeltaVersionOffset + kDeltaVersionSize;
+const uint64_t DeltaPerformer::kDeltaManifestSizeSize = 8;
+const uint64_t DeltaPerformer::kDeltaMetadataSignatureSizeSize = 4;
+const uint64_t DeltaPerformer::kMaxPayloadHeaderSize = 24;
+const uint64_t DeltaPerformer::kSupportedMajorPayloadVersion = 2;
+const uint32_t DeltaPerformer::kSupportedMinorPayloadVersion = 3;
+
+const unsigned DeltaPerformer::kProgressLogMaxChunks = 10;
+const unsigned DeltaPerformer::kProgressLogTimeoutSeconds = 30;
+const unsigned DeltaPerformer::kProgressDownloadWeight = 50;
+const unsigned DeltaPerformer::kProgressOperationsWeight = 50;
+
+namespace {
+const int kUpdateStateOperationInvalid = -1;
+const int kMaxResumedUpdateFailures = 10;
+#if USE_MTD
+const int kUbiVolumeAttachTimeout = 5 * 60;
+#endif
+
+FileDescriptorPtr CreateFileDescriptor(const char* path) {
+  FileDescriptorPtr ret;
+#if USE_MTD
+  if (strstr(path, "/dev/ubi") == path) {
+    if (!UbiFileDescriptor::IsUbi(path)) {
+      // The volume might not have been attached at boot time.
+      int volume_no;
+      if (utils::SplitPartitionName(path, nullptr, &volume_no)) {
+        utils::TryAttachingUbiVolume(volume_no, kUbiVolumeAttachTimeout);
+      }
+    }
+    if (UbiFileDescriptor::IsUbi(path)) {
+      LOG(INFO) << path << " is a UBI device.";
+      ret.reset(new UbiFileDescriptor);
+    }
+  } else if (MtdFileDescriptor::IsMtd(path)) {
+    LOG(INFO) << path << " is an MTD device.";
+    ret.reset(new MtdFileDescriptor);
+  } else {
+    LOG(INFO) << path << " is not an MTD nor a UBI device.";
+#endif
+    ret.reset(new EintrSafeFileDescriptor);
+#if USE_MTD
+  }
+#endif
+  return ret;
+}
+
+// Opens path for read/write. On success returns an open FileDescriptor
+// and sets *err to 0. On failure, sets *err to errno and returns nullptr.
+FileDescriptorPtr OpenFile(const char* path, int mode, int* err) {
+  FileDescriptorPtr fd = CreateFileDescriptor(path);
+#if USE_MTD
+  // On NAND devices, we can either read, or write, but not both. So here we
+  // use O_WRONLY.
+  if (UbiFileDescriptor::IsUbi(path) || MtdFileDescriptor::IsMtd(path)) {
+    mode = O_WRONLY;
+  }
+#endif
+  if (!fd->Open(path, mode, 000)) {
+    *err = errno;
+    PLOG(ERROR) << "Unable to open file " << path;
+    return nullptr;
+  }
+  *err = 0;
+  return fd;
+}
+}  // namespace
+
+
+// Computes the ratio of |part| and |total|, scaled to |norm|, using integer
+// arithmetic.
+static uint64_t IntRatio(uint64_t part, uint64_t total, uint64_t norm) {
+  return part * norm / total;
+}
+
+void DeltaPerformer::LogProgress(const char* message_prefix) {
+  // Format operations total count and percentage.
+  string total_operations_str("?");
+  string completed_percentage_str("");
+  if (num_total_operations_) {
+    total_operations_str = std::to_string(num_total_operations_);
+    // Upcasting to 64-bit to avoid overflow, back to size_t for formatting.
+    completed_percentage_str =
+        base::StringPrintf(" (%" PRIu64 "%%)",
+                           IntRatio(next_operation_num_, num_total_operations_,
+                                    100));
+  }
+
+  // Format download total count and percentage.
+  size_t payload_size = install_plan_->payload_size;
+  string payload_size_str("?");
+  string downloaded_percentage_str("");
+  if (payload_size) {
+    payload_size_str = std::to_string(payload_size);
+    // Upcasting to 64-bit to avoid overflow, back to size_t for formatting.
+    downloaded_percentage_str =
+        base::StringPrintf(" (%" PRIu64 "%%)",
+                           IntRatio(total_bytes_received_, payload_size, 100));
+  }
+
+  LOG(INFO) << (message_prefix ? message_prefix : "") << next_operation_num_
+            << "/" << total_operations_str << " operations"
+            << completed_percentage_str << ", " << total_bytes_received_
+            << "/" << payload_size_str << " bytes downloaded"
+            << downloaded_percentage_str << ", overall progress "
+            << overall_progress_ << "%";
+}
+
+void DeltaPerformer::UpdateOverallProgress(bool force_log,
+                                           const char* message_prefix) {
+  // Compute our download and overall progress.
+  unsigned new_overall_progress = 0;
+  COMPILE_ASSERT(kProgressDownloadWeight + kProgressOperationsWeight == 100,
+                 progress_weight_dont_add_up);
+  // Only consider download progress if its total size is known; otherwise
+  // adjust the operations weight to compensate for the absence of download
+  // progress. Also, make sure to cap the download portion at
+  // kProgressDownloadWeight, in case we end up downloading more than we
+  // initially expected (this indicates a problem, but could generally happen).
+  // TODO(garnold) the correction of operations weight when we do not have the
+  // total payload size, as well as the conditional guard below, should both be
+  // eliminated once we ensure that the payload_size in the install plan is
+  // always given and is non-zero. This currently isn't the case during unit
+  // tests (see chromium-os:37969).
+  size_t payload_size = install_plan_->payload_size;
+  unsigned actual_operations_weight = kProgressOperationsWeight;
+  if (payload_size)
+    new_overall_progress += min(
+        static_cast<unsigned>(IntRatio(total_bytes_received_, payload_size,
+                                       kProgressDownloadWeight)),
+        kProgressDownloadWeight);
+  else
+    actual_operations_weight += kProgressDownloadWeight;
+
+  // Only add completed operations if their total number is known; we definitely
+  // expect an update to have at least one operation, so the expectation is that
+  // this will eventually reach |actual_operations_weight|.
+  if (num_total_operations_)
+    new_overall_progress += IntRatio(next_operation_num_, num_total_operations_,
+                                     actual_operations_weight);
+
+  // Progress ratio cannot recede, unless our assumptions about the total
+  // payload size, total number of operations, or the monotonicity of progress
+  // is breached.
+  if (new_overall_progress < overall_progress_) {
+    LOG(WARNING) << "progress counter receded from " << overall_progress_
+                 << "% down to " << new_overall_progress << "%; this is a bug";
+    force_log = true;
+  }
+  overall_progress_ = new_overall_progress;
+
+  // Update chunk index, log as needed: if forced by called, or we completed a
+  // progress chunk, or a timeout has expired.
+  base::Time curr_time = base::Time::Now();
+  unsigned curr_progress_chunk =
+      overall_progress_ * kProgressLogMaxChunks / 100;
+  if (force_log || curr_progress_chunk > last_progress_chunk_ ||
+      curr_time > forced_progress_log_time_) {
+    forced_progress_log_time_ = curr_time + forced_progress_log_wait_;
+    LogProgress(message_prefix);
+  }
+  last_progress_chunk_ = curr_progress_chunk;
+}
+
+
+size_t DeltaPerformer::CopyDataToBuffer(const char** bytes_p, size_t* count_p,
+                                        size_t max) {
+  const size_t count = *count_p;
+  if (!count)
+    return 0;  // Special case shortcut.
+  size_t read_len = min(count, max - buffer_.size());
+  const char* bytes_start = *bytes_p;
+  const char* bytes_end = bytes_start + read_len;
+  buffer_.insert(buffer_.end(), bytes_start, bytes_end);
+  *bytes_p = bytes_end;
+  *count_p = count - read_len;
+  return read_len;
+}
+
+
+bool DeltaPerformer::HandleOpResult(bool op_result, const char* op_type_name,
+                                    ErrorCode* error) {
+  if (op_result)
+    return true;
+
+  LOG(ERROR) << "Failed to perform " << op_type_name << " operation "
+             << next_operation_num_;
+  *error = ErrorCode::kDownloadOperationExecutionError;
+  return false;
+}
+
+int DeltaPerformer::Close() {
+  int err = -CloseCurrentPartition();
+  LOG_IF(ERROR, !payload_hash_calculator_.Finalize() ||
+                !signed_hash_calculator_.Finalize())
+      << "Unable to finalize the hash.";
+  if (!buffer_.empty()) {
+    LOG(INFO) << "Discarding " << buffer_.size() << " unused downloaded bytes";
+    if (err >= 0)
+      err = 1;
+  }
+  return -err;
+}
+
+int DeltaPerformer::CloseCurrentPartition() {
+  int err = 0;
+  if (source_fd_ && !source_fd_->Close()) {
+    err = errno;
+    PLOG(ERROR) << "Error closing source partition";
+    if (!err)
+      err = 1;
+  }
+  source_fd_.reset();
+  source_path_.clear();
+
+  if (target_fd_ && !target_fd_->Close()) {
+    err = errno;
+    PLOG(ERROR) << "Error closing target partition";
+    if (!err)
+      err = 1;
+  }
+  target_fd_.reset();
+  target_path_.clear();
+  return -err;
+}
+
+bool DeltaPerformer::OpenCurrentPartition() {
+  if (current_partition_ >= partitions_.size())
+    return false;
+
+  const PartitionUpdate& partition = partitions_[current_partition_];
+  // Open source fds if we have a delta payload with minor version >= 2.
+  if (!install_plan_->is_full_update &&
+      GetMinorVersion() != kInPlaceMinorPayloadVersion) {
+    source_path_ = install_plan_->partitions[current_partition_].source_path;
+    int err;
+    source_fd_ = OpenFile(source_path_.c_str(), O_RDONLY, &err);
+    if (!source_fd_) {
+      LOG(ERROR) << "Unable to open source partition "
+                 << partition.partition_name() << " on slot "
+                 << BootControlInterface::SlotName(install_plan_->source_slot)
+                 << ", file " << source_path_;
+      return false;
+    }
+  }
+
+  target_path_ = install_plan_->partitions[current_partition_].target_path;
+  int err;
+  target_fd_ = OpenFile(target_path_.c_str(), O_RDWR, &err);
+  if (!target_fd_) {
+    LOG(ERROR) << "Unable to open target partition "
+               << partition.partition_name() << " on slot "
+               << BootControlInterface::SlotName(install_plan_->target_slot)
+               << ", file " << target_path_;
+    return false;
+  }
+  return true;
+}
+
+namespace {
+
+void LogPartitionInfoHash(const PartitionInfo& info, const string& tag) {
+  string sha256 = brillo::data_encoding::Base64Encode(info.hash());
+  LOG(INFO) << "PartitionInfo " << tag << " sha256: " << sha256
+            << " size: " << info.size();
+}
+
+void LogPartitionInfo(const vector<PartitionUpdate>& partitions) {
+  for (const PartitionUpdate& partition : partitions) {
+    LogPartitionInfoHash(partition.old_partition_info(),
+                         "old " + partition.partition_name());
+    LogPartitionInfoHash(partition.new_partition_info(),
+                         "new " + partition.partition_name());
+  }
+}
+
+}  // namespace
+
+bool DeltaPerformer::GetMetadataSignatureSizeOffset(
+    uint64_t* out_offset) const {
+  if (GetMajorVersion() == kBrilloMajorPayloadVersion) {
+    *out_offset = kDeltaManifestSizeOffset + kDeltaManifestSizeSize;
+    return true;
+  }
+  return false;
+}
+
+bool DeltaPerformer::GetManifestOffset(uint64_t* out_offset) const {
+  // Actual manifest begins right after the manifest size field or
+  // metadata signature size field if major version >= 2.
+  if (major_payload_version_ == kChromeOSMajorPayloadVersion) {
+    *out_offset = kDeltaManifestSizeOffset + kDeltaManifestSizeSize;
+    return true;
+  }
+  if (major_payload_version_ == kBrilloMajorPayloadVersion) {
+    *out_offset = kDeltaManifestSizeOffset + kDeltaManifestSizeSize +
+                  kDeltaMetadataSignatureSizeSize;
+    return true;
+  }
+  LOG(ERROR) << "Unknown major payload version: " << major_payload_version_;
+  return false;
+}
+
+uint64_t DeltaPerformer::GetMetadataSize() const {
+  return metadata_size_;
+}
+
+uint64_t DeltaPerformer::GetMajorVersion() const {
+  return major_payload_version_;
+}
+
+uint32_t DeltaPerformer::GetMinorVersion() const {
+  if (manifest_.has_minor_version()) {
+    return manifest_.minor_version();
+  } else {
+    return (install_plan_->is_full_update ?
+            kFullPayloadMinorVersion :
+            kSupportedMinorPayloadVersion);
+  }
+}
+
+bool DeltaPerformer::GetManifest(DeltaArchiveManifest* out_manifest_p) const {
+  if (!manifest_parsed_)
+    return false;
+  *out_manifest_p = manifest_;
+  return true;
+}
+
+bool DeltaPerformer::IsHeaderParsed() const {
+  return metadata_size_ != 0;
+}
+
+DeltaPerformer::MetadataParseResult DeltaPerformer::ParsePayloadMetadata(
+    const brillo::Blob& payload, ErrorCode* error) {
+  *error = ErrorCode::kSuccess;
+  uint64_t manifest_offset;
+
+  if (!IsHeaderParsed()) {
+    // Ensure we have data to cover the major payload version.
+    if (payload.size() < kDeltaManifestSizeOffset)
+      return kMetadataParseInsufficientData;
+
+    // Validate the magic string.
+    if (memcmp(payload.data(), kDeltaMagic, sizeof(kDeltaMagic)) != 0) {
+      LOG(ERROR) << "Bad payload format -- invalid delta magic.";
+      *error = ErrorCode::kDownloadInvalidMetadataMagicString;
+      return kMetadataParseError;
+    }
+
+    // Extract the payload version from the metadata.
+    COMPILE_ASSERT(sizeof(major_payload_version_) == kDeltaVersionSize,
+                   major_payload_version_size_mismatch);
+    memcpy(&major_payload_version_,
+           &payload[kDeltaVersionOffset],
+           kDeltaVersionSize);
+    // switch big endian to host
+    major_payload_version_ = be64toh(major_payload_version_);
+
+    if (major_payload_version_ != supported_major_version_ &&
+        major_payload_version_ != kChromeOSMajorPayloadVersion) {
+      LOG(ERROR) << "Bad payload format -- unsupported payload version: "
+          << major_payload_version_;
+      *error = ErrorCode::kUnsupportedMajorPayloadVersion;
+      return kMetadataParseError;
+    }
+
+    // Get the manifest offset now that we have payload version.
+    if (!GetManifestOffset(&manifest_offset)) {
+      *error = ErrorCode::kUnsupportedMajorPayloadVersion;
+      return kMetadataParseError;
+    }
+    // Check again with the manifest offset.
+    if (payload.size() < manifest_offset)
+      return kMetadataParseInsufficientData;
+
+    // Next, parse the manifest size.
+    COMPILE_ASSERT(sizeof(manifest_size_) == kDeltaManifestSizeSize,
+                   manifest_size_size_mismatch);
+    memcpy(&manifest_size_,
+           &payload[kDeltaManifestSizeOffset],
+           kDeltaManifestSizeSize);
+    manifest_size_ = be64toh(manifest_size_);  // switch big endian to host
+
+    if (GetMajorVersion() == kBrilloMajorPayloadVersion) {
+      // Parse the metadata signature size.
+      COMPILE_ASSERT(sizeof(metadata_signature_size_) ==
+                     kDeltaMetadataSignatureSizeSize,
+                     metadata_signature_size_size_mismatch);
+      uint64_t metadata_signature_size_offset;
+      if (!GetMetadataSignatureSizeOffset(&metadata_signature_size_offset)) {
+        *error = ErrorCode::kError;
+        return kMetadataParseError;
+      }
+      memcpy(&metadata_signature_size_,
+             &payload[metadata_signature_size_offset],
+             kDeltaMetadataSignatureSizeSize);
+      metadata_signature_size_ = be32toh(metadata_signature_size_);
+    }
+
+    // If the metadata size is present in install plan, check for it immediately
+    // even before waiting for that many number of bytes to be downloaded in the
+    // payload. This will prevent any attack which relies on us downloading data
+    // beyond the expected metadata size.
+    metadata_size_ = manifest_offset + manifest_size_;
+    if (install_plan_->hash_checks_mandatory) {
+      if (install_plan_->metadata_size != metadata_size_) {
+        LOG(ERROR) << "Mandatory metadata size in Omaha response ("
+                   << install_plan_->metadata_size
+                   << ") is missing/incorrect, actual = " << metadata_size_;
+        *error = ErrorCode::kDownloadInvalidMetadataSize;
+        return kMetadataParseError;
+      }
+    }
+  }
+
+  // Now that we have validated the metadata size, we should wait for the full
+  // metadata and its signature (if exist) to be read in before we can parse it.
+  if (payload.size() < metadata_size_ + metadata_signature_size_)
+    return kMetadataParseInsufficientData;
+
+  // Log whether we validated the size or simply trusting what's in the payload
+  // here. This is logged here (after we received the full metadata data) so
+  // that we just log once (instead of logging n times) if it takes n
+  // DeltaPerformer::Write calls to download the full manifest.
+  if (install_plan_->metadata_size == metadata_size_) {
+    LOG(INFO) << "Manifest size in payload matches expected value from Omaha";
+  } else {
+    // For mandatory-cases, we'd have already returned a kMetadataParseError
+    // above. We'll be here only for non-mandatory cases. Just send a UMA stat.
+    LOG(WARNING) << "Ignoring missing/incorrect metadata size ("
+                 << install_plan_->metadata_size
+                 << ") in Omaha response as validation is not mandatory. "
+                 << "Trusting metadata size in payload = " << metadata_size_;
+  }
+
+  // We have the full metadata in |payload|. Verify its integrity
+  // and authenticity based on the information we have in Omaha response.
+  *error = ValidateMetadataSignature(payload);
+  if (*error != ErrorCode::kSuccess) {
+    if (install_plan_->hash_checks_mandatory) {
+      // The autoupdate_CatchBadSignatures test checks for this string
+      // in log-files. Keep in sync.
+      LOG(ERROR) << "Mandatory metadata signature validation failed";
+      return kMetadataParseError;
+    }
+
+    // For non-mandatory cases, just send a UMA stat.
+    LOG(WARNING) << "Ignoring metadata signature validation failures";
+    *error = ErrorCode::kSuccess;
+  }
+
+  if (!GetManifestOffset(&manifest_offset)) {
+    *error = ErrorCode::kUnsupportedMajorPayloadVersion;
+    return kMetadataParseError;
+  }
+  // The payload metadata is deemed valid, it's safe to parse the protobuf.
+  if (!manifest_.ParseFromArray(&payload[manifest_offset], manifest_size_)) {
+    LOG(ERROR) << "Unable to parse manifest in update file.";
+    *error = ErrorCode::kDownloadManifestParseError;
+    return kMetadataParseError;
+  }
+
+  manifest_parsed_ = true;
+  return kMetadataParseSuccess;
+}
+
+// Wrapper around write. Returns true if all requested bytes
+// were written, or false on any error, regardless of progress
+// and stores an action exit code in |error|.
+bool DeltaPerformer::Write(const void* bytes, size_t count, ErrorCode *error) {
+  *error = ErrorCode::kSuccess;
+
+  const char* c_bytes = reinterpret_cast<const char*>(bytes);
+
+  // Update the total byte downloaded count and the progress logs.
+  total_bytes_received_ += count;
+  UpdateOverallProgress(false, "Completed ");
+
+  while (!manifest_valid_) {
+    // Read data up to the needed limit; this is either maximium payload header
+    // size, or the full metadata size (once it becomes known).
+    const bool do_read_header = !IsHeaderParsed();
+    CopyDataToBuffer(&c_bytes, &count,
+                     (do_read_header ? kMaxPayloadHeaderSize :
+                      metadata_size_ + metadata_signature_size_));
+
+    MetadataParseResult result = ParsePayloadMetadata(buffer_, error);
+    if (result == kMetadataParseError)
+      return false;
+    if (result == kMetadataParseInsufficientData) {
+      // If we just processed the header, make an attempt on the manifest.
+      if (do_read_header && IsHeaderParsed())
+        continue;
+
+      return true;
+    }
+
+    // Checks the integrity of the payload manifest.
+    if ((*error = ValidateManifest()) != ErrorCode::kSuccess)
+      return false;
+    manifest_valid_ = true;
+
+    // Clear the download buffer.
+    DiscardBuffer(false, metadata_size_);
+
+    // This populates |partitions_| and the |install_plan.partitions| with the
+    // list of partitions from the manifest.
+    if (!ParseManifestPartitions(error))
+      return false;
+
+    num_total_operations_ = 0;
+    for (const auto& partition : partitions_) {
+      num_total_operations_ += partition.operations_size();
+      acc_num_operations_.push_back(num_total_operations_);
+    }
+
+    LOG_IF(WARNING, !prefs_->SetInt64(kPrefsManifestMetadataSize,
+                                      metadata_size_))
+        << "Unable to save the manifest metadata size.";
+
+    if (!PrimeUpdateState()) {
+      *error = ErrorCode::kDownloadStateInitializationError;
+      LOG(ERROR) << "Unable to prime the update state.";
+      return false;
+    }
+
+    if (!OpenCurrentPartition()) {
+      *error = ErrorCode::kInstallDeviceOpenError;
+      return false;
+    }
+
+    if (next_operation_num_ > 0)
+      UpdateOverallProgress(true, "Resuming after ");
+    LOG(INFO) << "Starting to apply update payload operations";
+  }
+
+  while (next_operation_num_ < num_total_operations_) {
+    // Check if we should cancel the current attempt for any reason.
+    // In this case, *error will have already been populated with the reason
+    // why we're canceling.
+    if (download_delegate_ && download_delegate_->ShouldCancel(error))
+      return false;
+
+    // We know there are more operations to perform because we didn't reach the
+    // |num_total_operations_| limit yet.
+    while (next_operation_num_ >= acc_num_operations_[current_partition_]) {
+      CloseCurrentPartition();
+      current_partition_++;
+      if (!OpenCurrentPartition()) {
+        *error = ErrorCode::kInstallDeviceOpenError;
+        return false;
+      }
+    }
+    const size_t partition_operation_num = next_operation_num_ - (
+        current_partition_ ? acc_num_operations_[current_partition_ - 1] : 0);
+
+    const InstallOperation& op =
+        partitions_[current_partition_].operations(partition_operation_num);
+
+    CopyDataToBuffer(&c_bytes, &count, op.data_length());
+
+    // Check whether we received all of the next operation's data payload.
+    if (!CanPerformInstallOperation(op))
+      return true;
+
+    // Validate the operation only if the metadata signature is present.
+    // Otherwise, keep the old behavior. This serves as a knob to disable
+    // the validation logic in case we find some regression after rollout.
+    // NOTE: If hash checks are mandatory and if metadata_signature is empty,
+    // we would have already failed in ParsePayloadMetadata method and thus not
+    // even be here. So no need to handle that case again here.
+    if (!install_plan_->metadata_signature.empty()) {
+      // 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.
+
+    bool op_result;
+    switch (op.type()) {
+      case InstallOperation::REPLACE:
+      case InstallOperation::REPLACE_BZ:
+      case InstallOperation::REPLACE_XZ:
+        op_result = PerformReplaceOperation(op);
+        break;
+      case InstallOperation::ZERO:
+      case InstallOperation::DISCARD:
+        op_result = PerformZeroOrDiscardOperation(op);
+        break;
+      case InstallOperation::MOVE:
+        op_result = PerformMoveOperation(op);
+        break;
+      case InstallOperation::BSDIFF:
+        op_result = PerformBsdiffOperation(op);
+        break;
+      case InstallOperation::SOURCE_COPY:
+        op_result = PerformSourceCopyOperation(op);
+        break;
+      case InstallOperation::SOURCE_BSDIFF:
+        op_result = PerformSourceBsdiffOperation(op);
+        break;
+      default:
+       op_result = false;
+    }
+    if (!HandleOpResult(op_result, InstallOperationTypeName(op.type()), error))
+      return false;
+
+    next_operation_num_++;
+    UpdateOverallProgress(false, "Completed ");
+    CheckpointUpdateProgress();
+  }
+
+  // In major version 2, we don't add dummy operation to the payload.
+  if (major_payload_version_ == kBrilloMajorPayloadVersion &&
+      manifest_.has_signatures_offset() && manifest_.has_signatures_size()) {
+    if (manifest_.signatures_offset() != buffer_offset_) {
+      LOG(ERROR) << "Payload signatures offset points to blob offset "
+                 << manifest_.signatures_offset()
+                 << " but signatures are expected at offset "
+                 << buffer_offset_;
+      *error = ErrorCode::kDownloadPayloadVerificationError;
+      return false;
+    }
+    CopyDataToBuffer(&c_bytes, &count, manifest_.signatures_size());
+    // Needs more data to cover entire signature.
+    if (buffer_.size() < manifest_.signatures_size())
+      return true;
+    if (!ExtractSignatureMessage()) {
+      LOG(ERROR) << "Extract payload signature failed.";
+      *error = ErrorCode::kDownloadPayloadVerificationError;
+      return false;
+    }
+    DiscardBuffer(true, 0);
+  }
+
+  return true;
+}
+
+bool DeltaPerformer::IsManifestValid() {
+  return manifest_valid_;
+}
+
+bool DeltaPerformer::ParseManifestPartitions(ErrorCode* error) {
+  if (major_payload_version_ == kBrilloMajorPayloadVersion) {
+    partitions_.clear();
+    for (const PartitionUpdate& partition : manifest_.partitions()) {
+      partitions_.push_back(partition);
+    }
+    manifest_.clear_partitions();
+  } else if (major_payload_version_ == kChromeOSMajorPayloadVersion) {
+    LOG(INFO) << "Converting update information from old format.";
+    PartitionUpdate root_part;
+    root_part.set_partition_name(kLegacyPartitionNameRoot);
+#ifdef __ANDROID__
+    LOG(WARNING) << "Legacy payload major version provided to an Android "
+                    "build. Assuming no post-install. Please use major version "
+                    "2 or newer.";
+    root_part.set_run_postinstall(false);
+#else
+    root_part.set_run_postinstall(true);
+#endif  // __ANDROID__
+    if (manifest_.has_old_rootfs_info()) {
+      *root_part.mutable_old_partition_info() = manifest_.old_rootfs_info();
+      manifest_.clear_old_rootfs_info();
+    }
+    if (manifest_.has_new_rootfs_info()) {
+      *root_part.mutable_new_partition_info() = manifest_.new_rootfs_info();
+      manifest_.clear_new_rootfs_info();
+    }
+    *root_part.mutable_operations() = manifest_.install_operations();
+    manifest_.clear_install_operations();
+    partitions_.push_back(std::move(root_part));
+
+    PartitionUpdate kern_part;
+    kern_part.set_partition_name(kLegacyPartitionNameKernel);
+    kern_part.set_run_postinstall(false);
+    if (manifest_.has_old_kernel_info()) {
+      *kern_part.mutable_old_partition_info() = manifest_.old_kernel_info();
+      manifest_.clear_old_kernel_info();
+    }
+    if (manifest_.has_new_kernel_info()) {
+      *kern_part.mutable_new_partition_info() = manifest_.new_kernel_info();
+      manifest_.clear_new_kernel_info();
+    }
+    *kern_part.mutable_operations() = manifest_.kernel_install_operations();
+    manifest_.clear_kernel_install_operations();
+    partitions_.push_back(std::move(kern_part));
+  }
+
+  // TODO(deymo): Remove this block of code once we switched to optional
+  // source partition verification. This list of partitions in the InstallPlan
+  // is initialized with the expected hashes in the payload major version 1,
+  // so we need to check those now if already set. See b/23182225.
+  if (!install_plan_->partitions.empty()) {
+    if (!VerifySourcePartitions()) {
+      *error = ErrorCode::kDownloadStateInitializationError;
+      return false;
+    }
+  }
+
+  // Fill in the InstallPlan::partitions based on the partitions from the
+  // payload.
+  install_plan_->partitions.clear();
+  for (const auto& partition : partitions_) {
+    InstallPlan::Partition install_part;
+    install_part.name = partition.partition_name();
+    install_part.run_postinstall =
+        partition.has_run_postinstall() && partition.run_postinstall();
+
+    if (partition.has_old_partition_info()) {
+      const PartitionInfo& info = partition.old_partition_info();
+      install_part.source_size = info.size();
+      install_part.source_hash.assign(info.hash().begin(), info.hash().end());
+    }
+
+    if (!partition.has_new_partition_info()) {
+      LOG(ERROR) << "Unable to get new partition hash info on partition "
+                 << install_part.name << ".";
+      *error = ErrorCode::kDownloadNewPartitionInfoError;
+      return false;
+    }
+    const PartitionInfo& info = partition.new_partition_info();
+    install_part.target_size = info.size();
+    install_part.target_hash.assign(info.hash().begin(), info.hash().end());
+
+    install_plan_->partitions.push_back(install_part);
+  }
+
+  if (!install_plan_->LoadPartitionsFromSlots(boot_control_)) {
+    LOG(ERROR) << "Unable to determine all the partition devices.";
+    *error = ErrorCode::kInstallDeviceOpenError;
+    return false;
+  }
+  LogPartitionInfo(partitions_);
+  return true;
+}
+
+bool DeltaPerformer::CanPerformInstallOperation(
+    const chromeos_update_engine::InstallOperation& operation) {
+  // Move and source_copy operations don't require any data blob, so they can
+  // always be performed.
+  if (operation.type() == InstallOperation::MOVE ||
+      operation.type() == InstallOperation::SOURCE_COPY)
+    return true;
+
+  // See if we have the entire data blob in the buffer
+  if (operation.data_offset() < buffer_offset_) {
+    LOG(ERROR) << "we threw away data it seems?";
+    return false;
+  }
+
+  return (operation.data_offset() + operation.data_length() <=
+          buffer_offset_ + buffer_.size());
+}
+
+bool DeltaPerformer::PerformReplaceOperation(
+    const InstallOperation& operation) {
+  CHECK(operation.type() == InstallOperation::REPLACE ||
+        operation.type() == InstallOperation::REPLACE_BZ ||
+        operation.type() == InstallOperation::REPLACE_XZ);
+
+  // Since we delete data off the beginning of the buffer as we use it,
+  // the data we need should be exactly at the beginning of the buffer.
+  TEST_AND_RETURN_FALSE(buffer_offset_ == operation.data_offset());
+  TEST_AND_RETURN_FALSE(buffer_.size() >= operation.data_length());
+
+  // Extract the signature message if it's in this operation.
+  if (ExtractSignatureMessageFromOperation(operation)) {
+    // If this is dummy replace operation, we ignore it after extracting the
+    // signature.
+    DiscardBuffer(true, 0);
+    return true;
+  }
+
+  // Setup the ExtentWriter stack based on the operation type.
+  std::unique_ptr<ExtentWriter> writer =
+    brillo::make_unique_ptr(new ZeroPadExtentWriter(
+      brillo::make_unique_ptr(new DirectExtentWriter())));
+
+  if (operation.type() == InstallOperation::REPLACE_BZ) {
+    writer.reset(new BzipExtentWriter(std::move(writer)));
+  } else if (operation.type() == InstallOperation::REPLACE_XZ) {
+    writer.reset(new XzExtentWriter(std::move(writer)));
+  }
+
+  // Create a vector of extents to pass to the ExtentWriter.
+  vector<Extent> extents;
+  for (int i = 0; i < operation.dst_extents_size(); i++) {
+    extents.push_back(operation.dst_extents(i));
+  }
+
+  TEST_AND_RETURN_FALSE(writer->Init(target_fd_, extents, block_size_));
+  TEST_AND_RETURN_FALSE(writer->Write(buffer_.data(), operation.data_length()));
+  TEST_AND_RETURN_FALSE(writer->End());
+
+  // Update buffer
+  DiscardBuffer(true, buffer_.size());
+  return true;
+}
+
+bool DeltaPerformer::PerformZeroOrDiscardOperation(
+    const InstallOperation& operation) {
+  CHECK(operation.type() == InstallOperation::DISCARD ||
+        operation.type() == InstallOperation::ZERO);
+
+  // These operations have no blob.
+  TEST_AND_RETURN_FALSE(!operation.has_data_offset());
+  TEST_AND_RETURN_FALSE(!operation.has_data_length());
+
+  int request =
+      (operation.type() == InstallOperation::ZERO ? BLKZEROOUT : BLKDISCARD);
+
+  bool attempt_ioctl = true;
+  brillo::Blob zeros;
+  for (int i = 0; i < operation.dst_extents_size(); i++) {
+    Extent extent = operation.dst_extents(i);
+    const uint64_t start = extent.start_block() * block_size_;
+    const uint64_t length = extent.num_blocks() * block_size_;
+    if (attempt_ioctl) {
+      int result = 0;
+      if (target_fd_->BlkIoctl(request, start, length, &result) && result == 0)
+        continue;
+      attempt_ioctl = false;
+      zeros.resize(16 * block_size_);
+    }
+    // In case of failure, we fall back to writing 0 to the selected region.
+    for (uint64_t offset = 0; offset < length; offset += zeros.size()) {
+      uint64_t chunk_length = min(length - offset,
+                                  static_cast<uint64_t>(zeros.size()));
+      TEST_AND_RETURN_FALSE(
+          utils::PWriteAll(target_fd_, zeros.data(), chunk_length, start + offset));
+    }
+  }
+  return true;
+}
+
+bool DeltaPerformer::PerformMoveOperation(const InstallOperation& operation) {
+  // Calculate buffer size. Note, this function doesn't do a sliding
+  // window to copy in case the source and destination blocks overlap.
+  // If we wanted to do a sliding window, we could program the server
+  // to generate deltas that effectively did a sliding window.
+
+  uint64_t blocks_to_read = 0;
+  for (int i = 0; i < operation.src_extents_size(); i++)
+    blocks_to_read += operation.src_extents(i).num_blocks();
+
+  uint64_t blocks_to_write = 0;
+  for (int i = 0; i < operation.dst_extents_size(); i++)
+    blocks_to_write += operation.dst_extents(i).num_blocks();
+
+  DCHECK_EQ(blocks_to_write, blocks_to_read);
+  brillo::Blob buf(blocks_to_write * block_size_);
+
+  // Read in bytes.
+  ssize_t bytes_read = 0;
+  for (int i = 0; i < operation.src_extents_size(); i++) {
+    ssize_t bytes_read_this_iteration = 0;
+    const Extent& extent = operation.src_extents(i);
+    const size_t bytes = extent.num_blocks() * block_size_;
+    TEST_AND_RETURN_FALSE(extent.start_block() != kSparseHole);
+    TEST_AND_RETURN_FALSE(utils::PReadAll(target_fd_,
+                                          &buf[bytes_read],
+                                          bytes,
+                                          extent.start_block() * block_size_,
+                                          &bytes_read_this_iteration));
+    TEST_AND_RETURN_FALSE(
+        bytes_read_this_iteration == static_cast<ssize_t>(bytes));
+    bytes_read += bytes_read_this_iteration;
+  }
+
+  // Write bytes out.
+  ssize_t bytes_written = 0;
+  for (int i = 0; i < operation.dst_extents_size(); i++) {
+    const Extent& extent = operation.dst_extents(i);
+    const size_t bytes = extent.num_blocks() * block_size_;
+    TEST_AND_RETURN_FALSE(extent.start_block() != kSparseHole);
+    TEST_AND_RETURN_FALSE(utils::PWriteAll(target_fd_,
+                                           &buf[bytes_written],
+                                           bytes,
+                                           extent.start_block() * block_size_));
+    bytes_written += bytes;
+  }
+  DCHECK_EQ(bytes_written, bytes_read);
+  DCHECK_EQ(bytes_written, static_cast<ssize_t>(buf.size()));
+  return true;
+}
+
+namespace {
+
+// Takes |extents| and fills an empty vector |blocks| with a block index for
+// each block in |extents|. For example, [(3, 2), (8, 1)] would give [3, 4, 8].
+void ExtentsToBlocks(const RepeatedPtrField<Extent>& extents,
+                     vector<uint64_t>* blocks) {
+  for (Extent ext : extents) {
+    for (uint64_t j = 0; j < ext.num_blocks(); j++)
+      blocks->push_back(ext.start_block() + j);
+  }
+}
+
+// Takes |extents| and returns the number of blocks in those extents.
+uint64_t GetBlockCount(const RepeatedPtrField<Extent>& extents) {
+  uint64_t sum = 0;
+  for (Extent ext : extents) {
+    sum += ext.num_blocks();
+  }
+  return sum;
+}
+
+// Compare |calculated_hash| with source hash in |operation|, return false and
+// dump hash if don't match.
+bool ValidateSourceHash(const brillo::Blob& calculated_hash,
+                        const InstallOperation& operation) {
+  brillo::Blob expected_source_hash(operation.src_sha256_hash().begin(),
+                                    operation.src_sha256_hash().end());
+  if (calculated_hash != expected_source_hash) {
+    LOG(ERROR) << "Hash verification failed. Expected hash = ";
+    utils::HexDumpVector(expected_source_hash);
+    LOG(ERROR) << "Calculated hash = ";
+    utils::HexDumpVector(calculated_hash);
+    return false;
+  }
+  return true;
+}
+
+}  // namespace
+
+bool DeltaPerformer::PerformSourceCopyOperation(
+    const InstallOperation& operation) {
+  if (operation.has_src_length())
+    TEST_AND_RETURN_FALSE(operation.src_length() % block_size_ == 0);
+  if (operation.has_dst_length())
+    TEST_AND_RETURN_FALSE(operation.dst_length() % block_size_ == 0);
+
+  uint64_t blocks_to_read = GetBlockCount(operation.src_extents());
+  uint64_t blocks_to_write = GetBlockCount(operation.dst_extents());
+  TEST_AND_RETURN_FALSE(blocks_to_write ==  blocks_to_read);
+
+  // Create vectors of all the individual src/dst blocks.
+  vector<uint64_t> src_blocks;
+  vector<uint64_t> dst_blocks;
+  ExtentsToBlocks(operation.src_extents(), &src_blocks);
+  ExtentsToBlocks(operation.dst_extents(), &dst_blocks);
+  DCHECK_EQ(src_blocks.size(), blocks_to_read);
+  DCHECK_EQ(src_blocks.size(), dst_blocks.size());
+
+  brillo::Blob buf(block_size_);
+  ssize_t bytes_read = 0;
+  HashCalculator source_hasher;
+  // Read/write one block at a time.
+  for (uint64_t i = 0; i < blocks_to_read; i++) {
+    ssize_t bytes_read_this_iteration = 0;
+    uint64_t src_block = src_blocks[i];
+    uint64_t dst_block = dst_blocks[i];
+
+    // Read in bytes.
+    TEST_AND_RETURN_FALSE(
+        utils::PReadAll(source_fd_,
+                        buf.data(),
+                        block_size_,
+                        src_block * block_size_,
+                        &bytes_read_this_iteration));
+
+    // Write bytes out.
+    TEST_AND_RETURN_FALSE(
+        utils::PWriteAll(target_fd_,
+                         buf.data(),
+                         block_size_,
+                         dst_block * block_size_));
+
+    bytes_read += bytes_read_this_iteration;
+    TEST_AND_RETURN_FALSE(bytes_read_this_iteration ==
+                          static_cast<ssize_t>(block_size_));
+
+    if (operation.has_src_sha256_hash())
+      TEST_AND_RETURN_FALSE(source_hasher.Update(buf.data(), buf.size()));
+  }
+
+  if (operation.has_src_sha256_hash()) {
+    TEST_AND_RETURN_FALSE(source_hasher.Finalize());
+    TEST_AND_RETURN_FALSE(
+        ValidateSourceHash(source_hasher.raw_hash(), operation));
+  }
+
+  DCHECK_EQ(bytes_read, static_cast<ssize_t>(blocks_to_read * block_size_));
+  return true;
+}
+
+bool DeltaPerformer::ExtentsToBsdiffPositionsString(
+    const RepeatedPtrField<Extent>& extents,
+    uint64_t block_size,
+    uint64_t full_length,
+    string* positions_string) {
+  string ret;
+  uint64_t length = 0;
+  for (int i = 0; i < extents.size(); i++) {
+    Extent extent = extents.Get(i);
+    int64_t start = extent.start_block() * block_size;
+    uint64_t this_length = min(full_length - length,
+                               extent.num_blocks() * block_size);
+    ret += base::StringPrintf("%" PRIi64 ":%" PRIu64 ",", start, this_length);
+    length += this_length;
+  }
+  TEST_AND_RETURN_FALSE(length == full_length);
+  if (!ret.empty())
+    ret.resize(ret.size() - 1);  // Strip trailing comma off
+  *positions_string = ret;
+  return true;
+}
+
+bool DeltaPerformer::PerformBsdiffOperation(const InstallOperation& operation) {
+  // Since we delete data off the beginning of the buffer as we use it,
+  // the data we need should be exactly at the beginning of the buffer.
+  TEST_AND_RETURN_FALSE(buffer_offset_ == operation.data_offset());
+  TEST_AND_RETURN_FALSE(buffer_.size() >= operation.data_length());
+
+  string input_positions;
+  TEST_AND_RETURN_FALSE(ExtentsToBsdiffPositionsString(operation.src_extents(),
+                                                       block_size_,
+                                                       operation.src_length(),
+                                                       &input_positions));
+  string output_positions;
+  TEST_AND_RETURN_FALSE(ExtentsToBsdiffPositionsString(operation.dst_extents(),
+                                                       block_size_,
+                                                       operation.dst_length(),
+                                                       &output_positions));
+
+  string temp_filename;
+  TEST_AND_RETURN_FALSE(utils::MakeTempFile("au_patch.XXXXXX",
+                                            &temp_filename,
+                                            nullptr));
+  ScopedPathUnlinker path_unlinker(temp_filename);
+  {
+    int fd = open(temp_filename.c_str(), O_WRONLY | O_CREAT | O_TRUNC, 0644);
+    ScopedFdCloser fd_closer(&fd);
+    TEST_AND_RETURN_FALSE(
+        utils::WriteAll(fd, buffer_.data(), operation.data_length()));
+  }
+
+  // Update the buffer to release the patch data memory as soon as the patch
+  // file is written out.
+  DiscardBuffer(true, buffer_.size());
+
+  vector<string> cmd{kBspatchPath, target_path_, target_path_, temp_filename,
+                     input_positions, output_positions};
+
+  int return_code = 0;
+  TEST_AND_RETURN_FALSE(
+      Subprocess::SynchronousExecFlags(cmd, Subprocess::kSearchPath,
+                                       &return_code, nullptr));
+  TEST_AND_RETURN_FALSE(return_code == 0);
+
+  if (operation.dst_length() % block_size_) {
+    // Zero out rest of final block.
+    // TODO(adlr): build this into bspatch; it's more efficient that way.
+    const Extent& last_extent =
+        operation.dst_extents(operation.dst_extents_size() - 1);
+    const uint64_t end_byte =
+        (last_extent.start_block() + last_extent.num_blocks()) * block_size_;
+    const uint64_t begin_byte =
+        end_byte - (block_size_ - operation.dst_length() % block_size_);
+    brillo::Blob zeros(end_byte - begin_byte);
+    TEST_AND_RETURN_FALSE(
+        utils::PWriteAll(target_fd_, zeros.data(), end_byte - begin_byte, begin_byte));
+  }
+  return true;
+}
+
+bool DeltaPerformer::PerformSourceBsdiffOperation(
+    const InstallOperation& operation) {
+  // Since we delete data off the beginning of the buffer as we use it,
+  // the data we need should be exactly at the beginning of the buffer.
+  TEST_AND_RETURN_FALSE(buffer_offset_ == operation.data_offset());
+  TEST_AND_RETURN_FALSE(buffer_.size() >= operation.data_length());
+  if (operation.has_src_length())
+    TEST_AND_RETURN_FALSE(operation.src_length() % block_size_ == 0);
+  if (operation.has_dst_length())
+    TEST_AND_RETURN_FALSE(operation.dst_length() % block_size_ == 0);
+
+  if (operation.has_src_sha256_hash()) {
+    HashCalculator source_hasher;
+    const uint64_t kMaxBlocksToRead = 512;  // 2MB if block size is 4KB
+    brillo::Blob buf(kMaxBlocksToRead * block_size_);
+    for (const Extent& extent : operation.src_extents()) {
+      for (uint64_t i = 0; i < extent.num_blocks(); i += kMaxBlocksToRead) {
+        uint64_t blocks_to_read =
+            min(kMaxBlocksToRead, extent.num_blocks() - i);
+        ssize_t bytes_to_read = blocks_to_read * block_size_;
+        ssize_t bytes_read_this_iteration = 0;
+        TEST_AND_RETURN_FALSE(
+            utils::PReadAll(source_fd_, buf.data(), bytes_to_read,
+                            (extent.start_block() + i) * block_size_,
+                            &bytes_read_this_iteration));
+        TEST_AND_RETURN_FALSE(bytes_read_this_iteration == bytes_to_read);
+        TEST_AND_RETURN_FALSE(source_hasher.Update(buf.data(), bytes_to_read));
+      }
+    }
+    TEST_AND_RETURN_FALSE(source_hasher.Finalize());
+    TEST_AND_RETURN_FALSE(
+        ValidateSourceHash(source_hasher.raw_hash(), operation));
+  }
+
+  string input_positions;
+  TEST_AND_RETURN_FALSE(ExtentsToBsdiffPositionsString(operation.src_extents(),
+                                                       block_size_,
+                                                       operation.src_length(),
+                                                       &input_positions));
+  string output_positions;
+  TEST_AND_RETURN_FALSE(ExtentsToBsdiffPositionsString(operation.dst_extents(),
+                                                       block_size_,
+                                                       operation.dst_length(),
+                                                       &output_positions));
+
+  string temp_filename;
+  TEST_AND_RETURN_FALSE(utils::MakeTempFile("au_patch.XXXXXX",
+                                            &temp_filename,
+                                            nullptr));
+  ScopedPathUnlinker path_unlinker(temp_filename);
+  {
+    int fd = open(temp_filename.c_str(), O_WRONLY | O_CREAT | O_TRUNC, 0644);
+    ScopedFdCloser fd_closer(&fd);
+    TEST_AND_RETURN_FALSE(
+        utils::WriteAll(fd, buffer_.data(), operation.data_length()));
+  }
+
+  // Update the buffer to release the patch data memory as soon as the patch
+  // file is written out.
+  DiscardBuffer(true, buffer_.size());
+
+  vector<string> cmd{kBspatchPath, source_path_, target_path_, temp_filename,
+                     input_positions, output_positions};
+
+  int return_code = 0;
+  TEST_AND_RETURN_FALSE(
+      Subprocess::SynchronousExecFlags(cmd, Subprocess::kSearchPath,
+                                       &return_code, nullptr));
+  TEST_AND_RETURN_FALSE(return_code == 0);
+  return true;
+}
+
+bool DeltaPerformer::ExtractSignatureMessageFromOperation(
+    const InstallOperation& operation) {
+  if (operation.type() != InstallOperation::REPLACE ||
+      !manifest_.has_signatures_offset() ||
+      manifest_.signatures_offset() != operation.data_offset()) {
+    return false;
+  }
+  TEST_AND_RETURN_FALSE(manifest_.has_signatures_size() &&
+                        manifest_.signatures_size() == operation.data_length());
+  TEST_AND_RETURN_FALSE(ExtractSignatureMessage());
+  return true;
+}
+
+bool DeltaPerformer::ExtractSignatureMessage() {
+  TEST_AND_RETURN_FALSE(signatures_message_data_.empty());
+  TEST_AND_RETURN_FALSE(buffer_offset_ == manifest_.signatures_offset());
+  TEST_AND_RETURN_FALSE(buffer_.size() >= manifest_.signatures_size());
+  signatures_message_data_.assign(
+      buffer_.begin(),
+      buffer_.begin() + manifest_.signatures_size());
+
+  // Save the signature blob because if the update is interrupted after the
+  // download phase we don't go through this path anymore. Some alternatives to
+  // consider:
+  //
+  // 1. On resume, re-download the signature blob from the server and re-verify
+  // it.
+  //
+  // 2. Verify the signature as soon as it's received and don't checkpoint the
+  // blob and the signed sha-256 context.
+  LOG_IF(WARNING, !prefs_->SetString(kPrefsUpdateStateSignatureBlob,
+                                     string(signatures_message_data_.begin(),
+                                            signatures_message_data_.end())))
+      << "Unable to store the signature blob.";
+
+  LOG(INFO) << "Extracted signature data of size "
+            << manifest_.signatures_size() << " at "
+            << manifest_.signatures_offset();
+  return true;
+}
+
+bool DeltaPerformer::GetPublicKeyFromResponse(base::FilePath *out_tmp_key) {
+  if (hardware_->IsOfficialBuild() ||
+      utils::FileExists(public_key_path_.c_str()) ||
+      install_plan_->public_key_rsa.empty())
+    return false;
+
+  if (!utils::DecodeAndStoreBase64String(install_plan_->public_key_rsa,
+                                         out_tmp_key))
+    return false;
+
+  return true;
+}
+
+ErrorCode DeltaPerformer::ValidateMetadataSignature(
+    const brillo::Blob& payload) {
+  if (payload.size() < metadata_size_ + metadata_signature_size_)
+    return ErrorCode::kDownloadMetadataSignatureError;
+
+  brillo::Blob metadata_signature_blob, metadata_signature_protobuf_blob;
+  if (!install_plan_->metadata_signature.empty()) {
+    // Convert base64-encoded signature to raw bytes.
+    if (!brillo::data_encoding::Base64Decode(
+        install_plan_->metadata_signature, &metadata_signature_blob)) {
+      LOG(ERROR) << "Unable to decode base64 metadata signature: "
+                 << install_plan_->metadata_signature;
+      return ErrorCode::kDownloadMetadataSignatureError;
+    }
+  } else if (major_payload_version_ == kBrilloMajorPayloadVersion) {
+    metadata_signature_protobuf_blob.assign(payload.begin() + metadata_size_,
+                                            payload.begin() + metadata_size_ +
+                                            metadata_signature_size_);
+  }
+
+  if (metadata_signature_blob.empty() &&
+      metadata_signature_protobuf_blob.empty()) {
+    if (install_plan_->hash_checks_mandatory) {
+      LOG(ERROR) << "Missing mandatory metadata signature in both Omaha "
+                 << "response and payload.";
+      return ErrorCode::kDownloadMetadataSignatureMissingError;
+    }
+
+    LOG(WARNING) << "Cannot validate metadata as the signature is empty";
+    return ErrorCode::kSuccess;
+  }
+
+  // See if we should use the public RSA key in the Omaha response.
+  base::FilePath path_to_public_key(public_key_path_);
+  base::FilePath tmp_key;
+  if (GetPublicKeyFromResponse(&tmp_key))
+    path_to_public_key = tmp_key;
+  ScopedPathUnlinker tmp_key_remover(tmp_key.value());
+  if (tmp_key.empty())
+    tmp_key_remover.set_should_remove(false);
+
+  LOG(INFO) << "Verifying metadata hash signature using public key: "
+            << path_to_public_key.value();
+
+  HashCalculator metadata_hasher;
+  metadata_hasher.Update(payload.data(), metadata_size_);
+  if (!metadata_hasher.Finalize()) {
+    LOG(ERROR) << "Unable to compute actual hash of manifest";
+    return ErrorCode::kDownloadMetadataSignatureVerificationError;
+  }
+
+  brillo::Blob calculated_metadata_hash = metadata_hasher.raw_hash();
+  PayloadVerifier::PadRSA2048SHA256Hash(&calculated_metadata_hash);
+  if (calculated_metadata_hash.empty()) {
+    LOG(ERROR) << "Computed actual hash of metadata is empty.";
+    return ErrorCode::kDownloadMetadataSignatureVerificationError;
+  }
+
+  if (!metadata_signature_blob.empty()) {
+    brillo::Blob expected_metadata_hash;
+    if (!PayloadVerifier::GetRawHashFromSignature(metadata_signature_blob,
+                                                  path_to_public_key.value(),
+                                                  &expected_metadata_hash)) {
+      LOG(ERROR) << "Unable to compute expected hash from metadata signature";
+      return ErrorCode::kDownloadMetadataSignatureError;
+    }
+    if (calculated_metadata_hash != expected_metadata_hash) {
+      LOG(ERROR) << "Manifest hash verification failed. Expected hash = ";
+      utils::HexDumpVector(expected_metadata_hash);
+      LOG(ERROR) << "Calculated hash = ";
+      utils::HexDumpVector(calculated_metadata_hash);
+      return ErrorCode::kDownloadMetadataSignatureMismatch;
+    }
+  } else {
+    if (!PayloadVerifier::VerifySignature(metadata_signature_protobuf_blob,
+                                          path_to_public_key.value(),
+                                          calculated_metadata_hash)) {
+      LOG(ERROR) << "Manifest hash verification failed.";
+      return ErrorCode::kDownloadMetadataSignatureMismatch;
+    }
+  }
+
+  // The autoupdate_CatchBadSignatures test checks for this string in
+  // log-files. Keep in sync.
+  LOG(INFO) << "Metadata hash signature matches value in Omaha response.";
+  return ErrorCode::kSuccess;
+}
+
+ErrorCode DeltaPerformer::ValidateManifest() {
+  // Perform assorted checks to sanity check the manifest, make sure it
+  // matches data from other sources, and that it is a supported version.
+  //
+  // TODO(garnold) in general, the presence of an old partition hash should be
+  // the sole indicator for a delta update, as we would generally like update
+  // payloads to be self contained and not assume an Omaha response to tell us
+  // that. However, since this requires some massive reengineering of the update
+  // flow (making filesystem copying happen conditionally only *after*
+  // downloading and parsing of the update manifest) we'll put it off for now.
+  // See chromium-os:7597 for further discussion.
+  if (install_plan_->is_full_update) {
+    if (manifest_.has_old_kernel_info() || manifest_.has_old_rootfs_info()) {
+      LOG(ERROR) << "Purported full payload contains old partition "
+                    "hash(es), aborting update";
+      return ErrorCode::kPayloadMismatchedType;
+    }
+
+    for (const PartitionUpdate& partition : manifest_.partitions()) {
+      if (partition.has_old_partition_info()) {
+        LOG(ERROR) << "Purported full payload contains old partition "
+                      "hash(es), aborting update";
+        return ErrorCode::kPayloadMismatchedType;
+      }
+    }
+
+    if (manifest_.minor_version() != kFullPayloadMinorVersion) {
+      LOG(ERROR) << "Manifest contains minor version "
+                 << manifest_.minor_version()
+                 << ", but all full payloads should have version "
+                 << kFullPayloadMinorVersion << ".";
+      return ErrorCode::kUnsupportedMinorPayloadVersion;
+    }
+  } else {
+    if (manifest_.minor_version() != supported_minor_version_) {
+      LOG(ERROR) << "Manifest contains minor version "
+                 << manifest_.minor_version()
+                 << " not the supported "
+                 << supported_minor_version_;
+      return ErrorCode::kUnsupportedMinorPayloadVersion;
+    }
+  }
+
+  if (major_payload_version_ != kChromeOSMajorPayloadVersion) {
+    if (manifest_.has_old_rootfs_info() ||
+        manifest_.has_new_rootfs_info() ||
+        manifest_.has_old_kernel_info() ||
+        manifest_.has_new_kernel_info() ||
+        manifest_.install_operations_size() != 0 ||
+        manifest_.kernel_install_operations_size() != 0) {
+      LOG(ERROR) << "Manifest contains deprecated field only supported in "
+                 << "major payload version 1, but the payload major version is "
+                 << major_payload_version_;
+      return ErrorCode::kPayloadMismatchedType;
+    }
+  }
+
+  // TODO(garnold) we should be adding more and more manifest checks, such as
+  // partition boundaries etc (see chromium-os:37661).
+
+  return ErrorCode::kSuccess;
+}
+
+ErrorCode DeltaPerformer::ValidateOperationHash(
+    const InstallOperation& operation) {
+  if (!operation.data_sha256_hash().size()) {
+    if (!operation.data_length()) {
+      // Operations that do not have any data blob won't have any operation hash
+      // either. So, these operations are always considered validated since the
+      // metadata that contains all the non-data-blob portions of the operation
+      // has already been validated. This is true for both HTTP and HTTPS cases.
+      return ErrorCode::kSuccess;
+    }
+
+    // No hash is present for an operation that has data blobs. This shouldn't
+    // happen normally for any client that has this code, because the
+    // corresponding update should have been produced with the operation
+    // hashes. So if it happens it means either we've turned operation hash
+    // generation off in DeltaDiffGenerator or it's a regression of some sort.
+    // One caveat though: The last operation is a dummy signature operation
+    // that doesn't have a hash at the time the manifest is created. So we
+    // should not complaint about that operation. This operation can be
+    // recognized by the fact that it's offset is mentioned in the manifest.
+    if (manifest_.signatures_offset() &&
+        manifest_.signatures_offset() == operation.data_offset()) {
+      LOG(INFO) << "Skipping hash verification for signature operation "
+                << next_operation_num_ + 1;
+    } else {
+      if (install_plan_->hash_checks_mandatory) {
+        LOG(ERROR) << "Missing mandatory operation hash for operation "
+                   << next_operation_num_ + 1;
+        return ErrorCode::kDownloadOperationHashMissingError;
+      }
+
+      LOG(WARNING) << "Cannot validate operation " << next_operation_num_ + 1
+                   << " as there's no operation hash in manifest";
+    }
+    return ErrorCode::kSuccess;
+  }
+
+  brillo::Blob expected_op_hash;
+  expected_op_hash.assign(operation.data_sha256_hash().data(),
+                          (operation.data_sha256_hash().data() +
+                           operation.data_sha256_hash().size()));
+
+  HashCalculator operation_hasher;
+  operation_hasher.Update(buffer_.data(), operation.data_length());
+  if (!operation_hasher.Finalize()) {
+    LOG(ERROR) << "Unable to compute actual hash of operation "
+               << next_operation_num_;
+    return ErrorCode::kDownloadOperationHashVerificationError;
+  }
+
+  brillo::Blob calculated_op_hash = operation_hasher.raw_hash();
+  if (calculated_op_hash != expected_op_hash) {
+    LOG(ERROR) << "Hash verification failed for operation "
+               << next_operation_num_ << ". Expected hash = ";
+    utils::HexDumpVector(expected_op_hash);
+    LOG(ERROR) << "Calculated hash over " << operation.data_length()
+               << " bytes at offset: " << operation.data_offset() << " = ";
+    utils::HexDumpVector(calculated_op_hash);
+    return ErrorCode::kDownloadOperationHashMismatch;
+  }
+
+  return ErrorCode::kSuccess;
+}
+
+#define TEST_AND_RETURN_VAL(_retval, _condition)                \
+  do {                                                          \
+    if (!(_condition)) {                                        \
+      LOG(ERROR) << "VerifyPayload failure: " << #_condition;   \
+      return _retval;                                           \
+    }                                                           \
+  } while (0);
+
+ErrorCode DeltaPerformer::VerifyPayload(
+    const string& update_check_response_hash,
+    const uint64_t update_check_response_size) {
+
+  // See if we should use the public RSA key in the Omaha response.
+  base::FilePath path_to_public_key(public_key_path_);
+  base::FilePath tmp_key;
+  if (GetPublicKeyFromResponse(&tmp_key))
+    path_to_public_key = tmp_key;
+  ScopedPathUnlinker tmp_key_remover(tmp_key.value());
+  if (tmp_key.empty())
+    tmp_key_remover.set_should_remove(false);
+
+  LOG(INFO) << "Verifying payload using public key: "
+            << path_to_public_key.value();
+
+  // Verifies the download size.
+  TEST_AND_RETURN_VAL(ErrorCode::kPayloadSizeMismatchError,
+                      update_check_response_size ==
+                      metadata_size_ + metadata_signature_size_ +
+                      buffer_offset_);
+
+  // Verifies the payload hash.
+  const string& payload_hash_data = payload_hash_calculator_.hash();
+  TEST_AND_RETURN_VAL(ErrorCode::kDownloadPayloadVerificationError,
+                      !payload_hash_data.empty());
+  TEST_AND_RETURN_VAL(ErrorCode::kPayloadHashMismatchError,
+                      payload_hash_data == update_check_response_hash);
+
+  // Verifies the signed payload hash.
+  if (!utils::FileExists(path_to_public_key.value().c_str())) {
+    LOG(WARNING) << "Not verifying signed delta payload -- missing public key.";
+    return ErrorCode::kSuccess;
+  }
+  TEST_AND_RETURN_VAL(ErrorCode::kSignedDeltaPayloadExpectedError,
+                      !signatures_message_data_.empty());
+  brillo::Blob hash_data = signed_hash_calculator_.raw_hash();
+  TEST_AND_RETURN_VAL(ErrorCode::kDownloadPayloadPubKeyVerificationError,
+                      PayloadVerifier::PadRSA2048SHA256Hash(&hash_data));
+  TEST_AND_RETURN_VAL(ErrorCode::kDownloadPayloadPubKeyVerificationError,
+                      !hash_data.empty());
+
+  if (!PayloadVerifier::VerifySignature(
+      signatures_message_data_, path_to_public_key.value(), hash_data)) {
+    // The autoupdate_CatchBadSignatures test checks for this string
+    // in log-files. Keep in sync.
+    LOG(ERROR) << "Public key verification failed, thus update failed.";
+    return ErrorCode::kDownloadPayloadPubKeyVerificationError;
+  }
+
+  LOG(INFO) << "Payload hash matches value in payload.";
+
+  // At this point, we are guaranteed to have downloaded a full payload, i.e
+  // the one whose size matches the size mentioned in Omaha response. If any
+  // errors happen after this, it's likely a problem with the payload itself or
+  // the state of the system and not a problem with the URL or network.  So,
+  // indicate that to the download delegate so that AU can backoff
+  // appropriately.
+  if (download_delegate_)
+    download_delegate_->DownloadComplete();
+
+  return ErrorCode::kSuccess;
+}
+
+namespace {
+void LogVerifyError(const string& type,
+                    const string& device,
+                    uint64_t size,
+                    const string& local_hash,
+                    const string& expected_hash) {
+  LOG(ERROR) << "This is a server-side error due to "
+             << "mismatched delta update image!";
+  LOG(ERROR) << "The delta I've been given contains a " << type << " delta "
+             << "update that must be applied over a " << type << " with "
+             << "a specific checksum, but the " << type << " we're starting "
+             << "with doesn't have that checksum! This means that "
+             << "the delta I've been given doesn't match my existing "
+             << "system. The " << type << " partition I have has hash: "
+             << local_hash << " but the update expected me to have "
+             << expected_hash << " .";
+  LOG(INFO) << "To get the checksum of the " << type << " partition run this"
+               "command: dd if=" << device << " bs=1M count=" << size
+            << " iflag=count_bytes 2>/dev/null | openssl dgst -sha256 -binary "
+               "| openssl base64";
+  LOG(INFO) << "To get the checksum of partitions in a bin file, "
+            << "run: .../src/scripts/sha256_partitions.sh .../file.bin";
+}
+
+string StringForHashBytes(const void* bytes, size_t size) {
+  return brillo::data_encoding::Base64Encode(bytes, size);
+}
+}  // namespace
+
+bool DeltaPerformer::VerifySourcePartitions() {
+  LOG(INFO) << "Verifying source partitions.";
+  CHECK(manifest_valid_);
+  CHECK(install_plan_);
+  if (install_plan_->partitions.size() != partitions_.size()) {
+    DLOG(ERROR) << "The list of partitions in the InstallPlan doesn't match the "
+                   "list received in the payload. The InstallPlan has "
+                << install_plan_->partitions.size()
+                << " partitions while the payload has " << partitions_.size()
+                << " partitions.";
+    return false;
+  }
+  for (size_t i = 0; i < partitions_.size(); ++i) {
+    if (partitions_[i].partition_name() != install_plan_->partitions[i].name) {
+      DLOG(ERROR) << "The InstallPlan's partition " << i << " is \""
+                  << install_plan_->partitions[i].name
+                  << "\" but the payload expects it to be \""
+                  << partitions_[i].partition_name()
+                  << "\". This is an error in the DeltaPerformer setup.";
+      return false;
+    }
+    if (!partitions_[i].has_old_partition_info())
+      continue;
+    const PartitionInfo& info = partitions_[i].old_partition_info();
+    const InstallPlan::Partition& plan_part = install_plan_->partitions[i];
+    bool valid =
+        !plan_part.source_hash.empty() &&
+        plan_part.source_hash.size() == info.hash().size() &&
+        memcmp(plan_part.source_hash.data(),
+               info.hash().data(),
+               plan_part.source_hash.size()) == 0;
+    if (!valid) {
+      LogVerifyError(partitions_[i].partition_name(),
+                     plan_part.source_path,
+                     info.hash().size(),
+                     StringForHashBytes(plan_part.source_hash.data(),
+                                        plan_part.source_hash.size()),
+                     StringForHashBytes(info.hash().data(),
+                                        info.hash().size()));
+      return false;
+    }
+  }
+  return true;
+}
+
+void DeltaPerformer::DiscardBuffer(bool do_advance_offset,
+                                   size_t signed_hash_buffer_size) {
+  // Update the buffer offset.
+  if (do_advance_offset)
+    buffer_offset_ += buffer_.size();
+
+  // Hash the content.
+  payload_hash_calculator_.Update(buffer_.data(), buffer_.size());
+  signed_hash_calculator_.Update(buffer_.data(), signed_hash_buffer_size);
+
+  // Swap content with an empty vector to ensure that all memory is released.
+  brillo::Blob().swap(buffer_);
+}
+
+bool DeltaPerformer::CanResumeUpdate(PrefsInterface* prefs,
+                                     string update_check_response_hash) {
+  int64_t next_operation = kUpdateStateOperationInvalid;
+  if (!(prefs->GetInt64(kPrefsUpdateStateNextOperation, &next_operation) &&
+        next_operation != kUpdateStateOperationInvalid &&
+        next_operation > 0))
+    return false;
+
+  string interrupted_hash;
+  if (!(prefs->GetString(kPrefsUpdateCheckResponseHash, &interrupted_hash) &&
+        !interrupted_hash.empty() &&
+        interrupted_hash == update_check_response_hash))
+    return false;
+
+  int64_t resumed_update_failures;
+  if (!(prefs->GetInt64(kPrefsResumedUpdateFailures, &resumed_update_failures)
+        && resumed_update_failures > kMaxResumedUpdateFailures))
+    return false;
+
+  // Sanity check the rest.
+  int64_t next_data_offset = -1;
+  if (!(prefs->GetInt64(kPrefsUpdateStateNextDataOffset, &next_data_offset) &&
+        next_data_offset >= 0))
+    return false;
+
+  string sha256_context;
+  if (!(prefs->GetString(kPrefsUpdateStateSHA256Context, &sha256_context) &&
+        !sha256_context.empty()))
+    return false;
+
+  int64_t manifest_metadata_size = 0;
+  if (!(prefs->GetInt64(kPrefsManifestMetadataSize, &manifest_metadata_size) &&
+        manifest_metadata_size > 0))
+    return false;
+
+  return true;
+}
+
+bool DeltaPerformer::ResetUpdateProgress(PrefsInterface* prefs, bool quick) {
+  TEST_AND_RETURN_FALSE(prefs->SetInt64(kPrefsUpdateStateNextOperation,
+                                        kUpdateStateOperationInvalid));
+  if (!quick) {
+    prefs->SetString(kPrefsUpdateCheckResponseHash, "");
+    prefs->SetInt64(kPrefsUpdateStateNextDataOffset, -1);
+    prefs->SetInt64(kPrefsUpdateStateNextDataLength, 0);
+    prefs->SetString(kPrefsUpdateStateSHA256Context, "");
+    prefs->SetString(kPrefsUpdateStateSignedSHA256Context, "");
+    prefs->SetString(kPrefsUpdateStateSignatureBlob, "");
+    prefs->SetInt64(kPrefsManifestMetadataSize, -1);
+    prefs->SetInt64(kPrefsResumedUpdateFailures, 0);
+  }
+  return true;
+}
+
+bool DeltaPerformer::CheckpointUpdateProgress() {
+  Terminator::set_exit_blocked(true);
+  if (last_updated_buffer_offset_ != buffer_offset_) {
+    // Resets the progress in case we die in the middle of the state update.
+    ResetUpdateProgress(prefs_, true);
+    TEST_AND_RETURN_FALSE(
+        prefs_->SetString(kPrefsUpdateStateSHA256Context,
+                          payload_hash_calculator_.GetContext()));
+    TEST_AND_RETURN_FALSE(
+        prefs_->SetString(kPrefsUpdateStateSignedSHA256Context,
+                          signed_hash_calculator_.GetContext()));
+    TEST_AND_RETURN_FALSE(prefs_->SetInt64(kPrefsUpdateStateNextDataOffset,
+                                           buffer_offset_));
+    last_updated_buffer_offset_ = buffer_offset_;
+
+    if (next_operation_num_ < num_total_operations_) {
+      size_t partition_index = current_partition_;
+      while (next_operation_num_ >= acc_num_operations_[partition_index])
+        partition_index++;
+      const size_t partition_operation_num = next_operation_num_ - (
+          partition_index ? acc_num_operations_[partition_index - 1] : 0);
+      const InstallOperation& op =
+          partitions_[partition_index].operations(partition_operation_num);
+      TEST_AND_RETURN_FALSE(prefs_->SetInt64(kPrefsUpdateStateNextDataLength,
+                                             op.data_length()));
+    } else {
+      TEST_AND_RETURN_FALSE(prefs_->SetInt64(kPrefsUpdateStateNextDataLength,
+                                             0));
+    }
+  }
+  TEST_AND_RETURN_FALSE(prefs_->SetInt64(kPrefsUpdateStateNextOperation,
+                                         next_operation_num_));
+  return true;
+}
+
+bool DeltaPerformer::PrimeUpdateState() {
+  CHECK(manifest_valid_);
+  block_size_ = manifest_.block_size();
+
+  int64_t next_operation = kUpdateStateOperationInvalid;
+  if (!prefs_->GetInt64(kPrefsUpdateStateNextOperation, &next_operation) ||
+      next_operation == kUpdateStateOperationInvalid ||
+      next_operation <= 0) {
+    // Initiating a new update, no more state needs to be initialized.
+    return true;
+  }
+  next_operation_num_ = next_operation;
+
+  // Resuming an update -- load the rest of the update state.
+  int64_t next_data_offset = -1;
+  TEST_AND_RETURN_FALSE(prefs_->GetInt64(kPrefsUpdateStateNextDataOffset,
+                                         &next_data_offset) &&
+                        next_data_offset >= 0);
+  buffer_offset_ = next_data_offset;
+
+  // The signed hash context and the signature blob may be empty if the
+  // interrupted update didn't reach the signature.
+  string signed_hash_context;
+  if (prefs_->GetString(kPrefsUpdateStateSignedSHA256Context,
+                        &signed_hash_context)) {
+    TEST_AND_RETURN_FALSE(
+        signed_hash_calculator_.SetContext(signed_hash_context));
+  }
+
+  string signature_blob;
+  if (prefs_->GetString(kPrefsUpdateStateSignatureBlob, &signature_blob)) {
+    signatures_message_data_.assign(signature_blob.begin(),
+                                    signature_blob.end());
+  }
+
+  string hash_context;
+  TEST_AND_RETURN_FALSE(prefs_->GetString(kPrefsUpdateStateSHA256Context,
+                                          &hash_context) &&
+                        payload_hash_calculator_.SetContext(hash_context));
+
+  int64_t manifest_metadata_size = 0;
+  TEST_AND_RETURN_FALSE(prefs_->GetInt64(kPrefsManifestMetadataSize,
+                                         &manifest_metadata_size) &&
+                        manifest_metadata_size > 0);
+  metadata_size_ = manifest_metadata_size;
+
+  // Advance the download progress to reflect what doesn't need to be
+  // re-downloaded.
+  total_bytes_received_ += buffer_offset_;
+
+  // Speculatively count the resume as a failure.
+  int64_t resumed_update_failures;
+  if (prefs_->GetInt64(kPrefsResumedUpdateFailures, &resumed_update_failures)) {
+    resumed_update_failures++;
+  } else {
+    resumed_update_failures = 1;
+  }
+  prefs_->SetInt64(kPrefsResumedUpdateFailures, resumed_update_failures);
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/delta_performer.h b/payload_consumer/delta_performer.h
new file mode 100644
index 0000000..47ecfd8
--- /dev/null
+++ b/payload_consumer/delta_performer.h
@@ -0,0 +1,407 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_DELTA_PERFORMER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_DELTA_PERFORMER_H_
+
+#include <inttypes.h>
+
+#include <string>
+#include <vector>
+
+#include <base/time/time.h>
+#include <brillo/secure_blob.h>
+#include <google/protobuf/repeated_field.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/payload_consumer/file_descriptor.h"
+#include "update_engine/payload_consumer/file_writer.h"
+#include "update_engine/payload_consumer/install_plan.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+class DownloadActionDelegate;
+class BootControlInterface;
+class HardwareInterface;
+class PrefsInterface;
+
+// This class performs the actions in a delta update synchronously. The delta
+// update itself should be passed in in chunks as it is received.
+
+class DeltaPerformer : public FileWriter {
+ public:
+  enum MetadataParseResult {
+    kMetadataParseSuccess,
+    kMetadataParseError,
+    kMetadataParseInsufficientData,
+  };
+
+  static const uint64_t kDeltaVersionOffset;
+  static const uint64_t kDeltaVersionSize;
+  static const uint64_t kDeltaManifestSizeOffset;
+  static const uint64_t kDeltaManifestSizeSize;
+  static const uint64_t kDeltaMetadataSignatureSizeSize;
+  static const uint64_t kMaxPayloadHeaderSize;
+  static const uint64_t kSupportedMajorPayloadVersion;
+  static const uint32_t kSupportedMinorPayloadVersion;
+
+  // Defines the granularity of progress logging in terms of how many "completed
+  // chunks" we want to report at the most.
+  static const unsigned kProgressLogMaxChunks;
+  // Defines a timeout since the last progress was logged after which we want to
+  // force another log message (even if the current chunk was not completed).
+  static const unsigned kProgressLogTimeoutSeconds;
+  // These define the relative weights (0-100) we give to the different work
+  // components associated with an update when computing an overall progress.
+  // Currently they include the download progress and the number of completed
+  // operations. They must add up to one hundred (100).
+  static const unsigned kProgressDownloadWeight;
+  static const unsigned kProgressOperationsWeight;
+
+  DeltaPerformer(PrefsInterface* prefs,
+                 BootControlInterface* boot_control,
+                 HardwareInterface* hardware,
+                 DownloadActionDelegate* download_delegate,
+                 InstallPlan* install_plan)
+      : prefs_(prefs),
+        boot_control_(boot_control),
+        hardware_(hardware),
+        download_delegate_(download_delegate),
+        install_plan_(install_plan) {}
+
+  // FileWriter's Write implementation where caller doesn't care about
+  // error codes.
+  bool Write(const void* bytes, size_t count) override {
+    ErrorCode error;
+    return Write(bytes, count, &error);
+  }
+
+  // FileWriter's Write implementation that returns a more specific |error| code
+  // in case of failures in Write operation.
+  bool Write(const void* bytes, size_t count, ErrorCode *error) override;
+
+  // Wrapper around close. Returns 0 on success or -errno on error.
+  // Closes both 'path' given to Open() and the kernel path.
+  int Close() override;
+
+  // Open the target and source (if delta payload) file descriptors for the
+  // |current_partition_|. The manifest needs to be already parsed for this to
+  // work. Returns whether the required file descriptors were successfully open.
+  bool OpenCurrentPartition();
+
+  // Closes the current partition file descriptors if open. Returns 0 on success
+  // or -errno on error.
+  int CloseCurrentPartition();
+
+  // Returns |true| only if the manifest has been processed and it's valid.
+  bool IsManifestValid();
+
+  // Verifies the downloaded payload against the signed hash included in the
+  // payload, against the update check hash (which is in base64 format)  and
+  // size using the public key and returns ErrorCode::kSuccess on success, an
+  // error code on failure.  This method should be called after closing the
+  // stream. Note this method skips the signed hash check if the public key is
+  // unavailable; it returns ErrorCode::kSignedDeltaPayloadExpectedError if the
+  // public key is available but the delta payload doesn't include a signature.
+  ErrorCode VerifyPayload(const std::string& update_check_response_hash,
+                          const uint64_t update_check_response_size);
+
+  // Converts an ordered collection of Extent objects which contain data of
+  // length full_length to a comma-separated string. For each Extent, the
+  // string will have the start offset and then the length in bytes.
+  // The length value of the last extent in the string may be short, since
+  // the full length of all extents in the string is capped to full_length.
+  // Also, an extent starting at kSparseHole, appears as -1 in the string.
+  // For example, if the Extents are {1, 1}, {4, 2}, {kSparseHole, 1},
+  // {0, 1}, block_size is 4096, and full_length is 5 * block_size - 13,
+  // the resulting string will be: "4096:4096,16384:8192,-1:4096,0:4083"
+  static bool ExtentsToBsdiffPositionsString(
+      const google::protobuf::RepeatedPtrField<Extent>& extents,
+      uint64_t block_size,
+      uint64_t full_length,
+      std::string* positions_string);
+
+  // Returns true if a previous update attempt can be continued based on the
+  // persistent preferences and the new update check response hash.
+  static bool CanResumeUpdate(PrefsInterface* prefs,
+                              std::string update_check_response_hash);
+
+  // Resets the persistent update progress state to indicate that an update
+  // can't be resumed. Performs a quick update-in-progress reset if |quick| is
+  // true, otherwise resets all progress-related update state. Returns true on
+  // success, false otherwise.
+  static bool ResetUpdateProgress(PrefsInterface* prefs, bool quick);
+
+  // Attempts to parse the update metadata starting from the beginning of
+  // |payload|. On success, returns kMetadataParseSuccess. Returns
+  // kMetadataParseInsufficientData if more data is needed to parse the complete
+  // metadata. Returns kMetadataParseError if the metadata can't be parsed given
+  // the payload.
+  MetadataParseResult ParsePayloadMetadata(const brillo::Blob& payload,
+                                           ErrorCode* error);
+
+  void set_public_key_path(const std::string& public_key_path) {
+    public_key_path_ = public_key_path;
+  }
+
+  // Set |*out_offset| to the byte offset where the size of the metadata signature
+  // is stored in a payload. Return true on success, if this field is not
+  // present in the payload, return false.
+  bool GetMetadataSignatureSizeOffset(uint64_t* out_offset) const;
+
+  // Set |*out_offset| to the byte offset at which the manifest protobuf begins
+  // in a payload. Return true on success, false if the offset is unknown.
+  bool GetManifestOffset(uint64_t* out_offset) const;
+
+  // Returns the size of the payload metadata, which includes the payload header
+  // and the manifest. If the header was not yet parsed, returns zero.
+  uint64_t GetMetadataSize() const;
+
+  // If the manifest was successfully parsed, copies it to |*out_manifest_p|.
+  // Returns true on success.
+  bool GetManifest(DeltaArchiveManifest* out_manifest_p) const;
+
+  // Return true if header parsing is finished and no errors occurred.
+  bool IsHeaderParsed() const;
+
+  // Returns the major payload version. If the version was not yet parsed,
+  // returns zero.
+  uint64_t GetMajorVersion() const;
+
+  // Returns the delta minor version. If this value is defined in the manifest,
+  // it returns that value, otherwise it returns the default value.
+  uint32_t GetMinorVersion() const;
+
+ private:
+  friend class DeltaPerformerTest;
+  friend class DeltaPerformerIntegrationTest;
+  FRIEND_TEST(DeltaPerformerTest, BrilloMetadataSignatureSizeTest);
+  FRIEND_TEST(DeltaPerformerTest, BrilloVerifyMetadataSignatureTest);
+  FRIEND_TEST(DeltaPerformerTest, UsePublicKeyFromResponse);
+
+  // Parse and move the update instructions of all partitions into our local
+  // |partitions_| variable based on the version of the payload. Requires the
+  // manifest to be parsed and valid.
+  bool ParseManifestPartitions(ErrorCode* error);
+
+  // Appends up to |*count_p| bytes from |*bytes_p| to |buffer_|, but only to
+  // the extent that the size of |buffer_| does not exceed |max|. Advances
+  // |*cbytes_p| and decreases |*count_p| by the actual number of bytes copied,
+  // and returns this number.
+  size_t CopyDataToBuffer(const char** bytes_p, size_t* count_p, size_t max);
+
+  // If |op_result| is false, emits an error message using |op_type_name| and
+  // sets |*error| accordingly. Otherwise does nothing. Returns |op_result|.
+  bool HandleOpResult(bool op_result, const char* op_type_name,
+                      ErrorCode* error);
+
+  // Logs the progress of downloading/applying an update.
+  void LogProgress(const char* message_prefix);
+
+  // Update overall progress metrics, log as necessary.
+  void UpdateOverallProgress(bool force_log, const char* message_prefix);
+
+  // Verifies that the expected source partition hashes (if present) match the
+  // hashes for the current partitions. Returns true if there are no expected
+  // hashes in the payload (e.g., if it's a new-style full update) or if the
+  // hashes match; returns false otherwise.
+  bool VerifySourcePartitions();
+
+  // Returns true if enough of the delta file has been passed via Write()
+  // to be able to perform a given install operation.
+  bool CanPerformInstallOperation(const InstallOperation& operation);
+
+  // Checks the integrity of the payload manifest. Returns true upon success,
+  // false otherwise.
+  ErrorCode ValidateManifest();
+
+  // Validates that the hash of the blobs corresponding to the given |operation|
+  // matches what's specified in the manifest in the payload.
+  // Returns ErrorCode::kSuccess on match or a suitable error code otherwise.
+  ErrorCode ValidateOperationHash(const InstallOperation& operation);
+
+  // Given the |payload|, verifies that the signed hash of its metadata matches
+  // what's specified in the install plan from Omaha (if present) or the
+  // metadata signature in payload itself (if present). Returns
+  // ErrorCode::kSuccess on match or a suitable error code otherwise. This
+  // method must be called before any part of the metadata is parsed so that a
+  // man-in-the-middle attack on the SSL connection to the payload server
+  // doesn't exploit any vulnerability in the code that parses the protocol
+  // buffer.
+  ErrorCode ValidateMetadataSignature(const brillo::Blob& payload);
+
+  // Returns true on success.
+  bool PerformInstallOperation(const InstallOperation& operation);
+
+  // These perform a specific type of operation and return true on success.
+  bool PerformReplaceOperation(const InstallOperation& operation);
+  bool PerformZeroOrDiscardOperation(const InstallOperation& operation);
+  bool PerformMoveOperation(const InstallOperation& operation);
+  bool PerformBsdiffOperation(const InstallOperation& operation);
+  bool PerformSourceCopyOperation(const InstallOperation& operation);
+  bool PerformSourceBsdiffOperation(const InstallOperation& operation);
+
+  // Extracts the payload signature message from the blob on the |operation| if
+  // the offset matches the one specified by the manifest. Returns whether the
+  // signature was extracted.
+  bool ExtractSignatureMessageFromOperation(const InstallOperation& operation);
+
+  // Extracts the payload signature message from the current |buffer_| if the
+  // offset matches the one specified by the manifest. Returns whether the
+  // signature was extracted.
+  bool ExtractSignatureMessage();
+
+  // Updates the payload hash calculator with the bytes in |buffer_|, also
+  // updates the signed hash calculator with the first |signed_hash_buffer_size|
+  // bytes in |buffer_|. Then discard the content, ensuring that memory is being
+  // deallocated. If |do_advance_offset|, advances the internal offset counter
+  // accordingly.
+  void DiscardBuffer(bool do_advance_offset, size_t signed_hash_buffer_size);
+
+  // Checkpoints the update progress into persistent storage to allow this
+  // update attempt to be resumed after reboot.
+  bool CheckpointUpdateProgress();
+
+  // Primes the required update state. Returns true if the update state was
+  // successfully initialized to a saved resume state or if the update is a new
+  // update. Returns false otherwise.
+  bool PrimeUpdateState();
+
+  // If the Omaha response contains a public RSA key and we're allowed
+  // to use it (e.g. if we're in developer mode), extract the key from
+  // the response and store it in a temporary file and return true. In
+  // the affirmative the path to the temporary file is stored in
+  // |out_tmp_key| and it is the responsibility of the caller to clean
+  // it up.
+  bool GetPublicKeyFromResponse(base::FilePath *out_tmp_key);
+
+  // Update Engine preference store.
+  PrefsInterface* prefs_;
+
+  // BootControl and Hardware interface references.
+  BootControlInterface* boot_control_;
+  HardwareInterface* hardware_;
+
+  // The DownloadActionDelegate instance monitoring the DownloadAction, or a
+  // nullptr if not used.
+  DownloadActionDelegate* download_delegate_;
+
+  // Install Plan based on Omaha Response.
+  InstallPlan* install_plan_;
+
+  // File descriptor of the source partition. Only set while updating a
+  // partition when using a delta payload.
+  FileDescriptorPtr source_fd_{nullptr};
+
+  // File descriptor of the target partition. Only set while performing the
+  // operations of a given partition.
+  FileDescriptorPtr target_fd_{nullptr};
+
+  // Paths the |source_fd_| and |target_fd_| refer to.
+  std::string source_path_;
+  std::string target_path_;
+
+  // Parsed manifest. Set after enough bytes to parse the manifest were
+  // downloaded.
+  DeltaArchiveManifest manifest_;
+  bool manifest_parsed_{false};
+  bool manifest_valid_{false};
+  uint64_t metadata_size_{0};
+  uint64_t manifest_size_{0};
+  uint32_t metadata_signature_size_{0};
+  uint64_t major_payload_version_{0};
+
+  // Accumulated number of operations per partition. The i-th element is the
+  // sum of the number of operations for all the partitions from 0 to i
+  // inclusive. Valid when |manifest_valid_| is true.
+  std::vector<size_t> acc_num_operations_;
+
+  // The total operations in a payload. Valid when |manifest_valid_| is true,
+  // otherwise 0.
+  size_t num_total_operations_{0};
+
+  // The list of partitions to update as found in the manifest major version 2.
+  // When parsing an older manifest format, the information is converted over to
+  // this format instead.
+  std::vector<PartitionUpdate> partitions_;
+
+  // Index in the list of partitions (|partitions_| member) of the current
+  // partition being processed.
+  size_t current_partition_{0};
+
+  // Index of the next operation to perform in the manifest. The index is linear
+  // on the total number of operation on the manifest.
+  size_t next_operation_num_{0};
+
+  // A buffer used for accumulating downloaded data. Initially, it stores the
+  // payload metadata; once that's downloaded and parsed, it stores data for the
+  // next update operation.
+  brillo::Blob buffer_;
+  // Offset of buffer_ in the binary blobs section of the update.
+  uint64_t buffer_offset_{0};
+
+  // Last |buffer_offset_| value updated as part of the progress update.
+  uint64_t last_updated_buffer_offset_{kuint64max};
+
+  // The block size (parsed from the manifest).
+  uint32_t block_size_{0};
+
+  // Calculates the whole payload file hash, including headers and signatures.
+  HashCalculator payload_hash_calculator_;
+
+  // Calculates the hash of the portion of the payload signed by the payload
+  // signature. This hash skips the metadata signature portion, located after
+  // the metadata and doesn't include the payload signature itself.
+  HashCalculator signed_hash_calculator_;
+
+  // Signatures message blob extracted directly from the payload.
+  brillo::Blob signatures_message_data_;
+
+  // The public key to be used. Provided as a member so that tests can
+  // override with test keys.
+  std::string public_key_path_{constants::kUpdatePayloadPublicKeyPath};
+
+  // The number of bytes received so far, used for progress tracking.
+  size_t total_bytes_received_{0};
+
+  // An overall progress counter, which should reflect both download progress
+  // and the ratio of applied operations. Range is 0-100.
+  unsigned overall_progress_{0};
+
+  // The last progress chunk recorded.
+  unsigned last_progress_chunk_{0};
+
+  // The timeout after which we should force emitting a progress log (constant),
+  // and the actual point in time for the next forced log to be emitted.
+  const base::TimeDelta forced_progress_log_wait_{
+      base::TimeDelta::FromSeconds(kProgressLogTimeoutSeconds)};
+  base::Time forced_progress_log_time_;
+
+  // The payload major payload version supported by DeltaPerformer.
+  uint64_t supported_major_version_{kSupportedMajorPayloadVersion};
+
+  // The delta minor payload version supported by DeltaPerformer.
+  uint32_t supported_minor_version_{kSupportedMinorPayloadVersion};
+
+  DISALLOW_COPY_AND_ASSIGN(DeltaPerformer);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_DELTA_PERFORMER_H_
diff --git a/payload_consumer/delta_performer_integration_test.cc b/payload_consumer/delta_performer_integration_test.cc
new file mode 100644
index 0000000..bcf7db2
--- /dev/null
+++ b/payload_consumer/delta_performer_integration_test.cc
@@ -0,0 +1,1035 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/delta_performer.h"
+
+#include <inttypes.h>
+#include <sys/mount.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <google/protobuf/repeated_field.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/mock_prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/mock_download_action.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_consumer/payload_verifier.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/payload_signer.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+using std::string;
+using std::vector;
+using test_utils::ScopedLoopMounter;
+using test_utils::System;
+using test_utils::kRandomString;
+using testing::Return;
+using testing::_;
+
+extern const char* kUnittestPrivateKeyPath;
+extern const char* kUnittestPublicKeyPath;
+extern const char* kUnittestPrivateKey2Path;
+extern const char* kUnittestPublicKey2Path;
+
+static const int kDefaultKernelSize = 4096;  // Something small for a test
+static const uint8_t kNewData[] = {'T', 'h', 'i', 's', ' ', 'i', 's', ' ',
+                                   'n', 'e', 'w', ' ', 'd', 'a', 't', 'a', '.'};
+
+namespace {
+struct DeltaState {
+  string a_img;
+  string b_img;
+  string result_img;
+  size_t image_size;
+
+  string delta_path;
+  uint64_t metadata_size;
+
+  string old_kernel;
+  brillo::Blob old_kernel_data;
+
+  string new_kernel;
+  brillo::Blob new_kernel_data;
+
+  string result_kernel;
+  brillo::Blob result_kernel_data;
+  size_t kernel_size;
+
+  // The InstallPlan referenced by the DeltaPerformer. This needs to outlive
+  // the DeltaPerformer.
+  InstallPlan install_plan;
+
+  // The in-memory copy of delta file.
+  brillo::Blob delta;
+
+  // Mock and fake instances used by the delta performer.
+  FakeBootControl fake_boot_control_;
+  FakeHardware fake_hardware_;
+  MockDownloadActionDelegate mock_delegate_;
+};
+
+enum SignatureTest {
+  kSignatureNone,  // No payload signing.
+  kSignatureGenerator,  // Sign the payload at generation time.
+  kSignatureGenerated,  // Sign the payload after it's generated.
+  kSignatureGeneratedPlaceholder,  // Insert placeholder signatures, then real.
+  kSignatureGeneratedPlaceholderMismatch,  // Insert a wrong sized placeholder.
+  kSignatureGeneratedShell,  // Sign the generated payload through shell cmds.
+  kSignatureGeneratedShellBadKey,  // Sign with a bad key through shell cmds.
+  kSignatureGeneratedShellRotateCl1,  // Rotate key, test client v1
+  kSignatureGeneratedShellRotateCl2,  // Rotate key, test client v2
+};
+
+enum OperationHashTest {
+  kInvalidOperationData,
+  kValidOperationData,
+};
+
+}  // namespace
+
+class DeltaPerformerIntegrationTest : public ::testing::Test {
+ public:
+  static void SetSupportedVersion(DeltaPerformer* performer,
+                                  uint64_t minor_version) {
+    performer->supported_minor_version_ = minor_version;
+  }
+};
+
+static void CompareFilesByBlock(const string& a_file, const string& b_file,
+                                size_t image_size) {
+  EXPECT_EQ(0, image_size % kBlockSize);
+
+  brillo::Blob a_data, b_data;
+  EXPECT_TRUE(utils::ReadFile(a_file, &a_data)) << "file failed: " << a_file;
+  EXPECT_TRUE(utils::ReadFile(b_file, &b_data)) << "file failed: " << b_file;
+
+  EXPECT_GE(a_data.size(), image_size);
+  EXPECT_GE(b_data.size(), image_size);
+  for (size_t i = 0; i < image_size; i += kBlockSize) {
+    EXPECT_EQ(0, i % kBlockSize);
+    brillo::Blob a_sub(&a_data[i], &a_data[i + kBlockSize]);
+    brillo::Blob b_sub(&b_data[i], &b_data[i + kBlockSize]);
+    EXPECT_TRUE(a_sub == b_sub) << "Block " << (i/kBlockSize) << " differs";
+  }
+  if (::testing::Test::HasNonfatalFailure()) {
+    LOG(INFO) << "Compared filesystems with size " << image_size
+              << ", partition A " << a_file << " size: " << a_data.size()
+              << ", partition B " << b_file << " size: " << b_data.size();
+  }
+}
+
+static bool WriteSparseFile(const string& path, off_t size) {
+  int fd = open(path.c_str(), O_CREAT | O_TRUNC | O_WRONLY, 0644);
+  TEST_AND_RETURN_FALSE_ERRNO(fd >= 0);
+  ScopedFdCloser fd_closer(&fd);
+  off_t rc = lseek(fd, size + 1, SEEK_SET);
+  TEST_AND_RETURN_FALSE_ERRNO(rc != static_cast<off_t>(-1));
+  int return_code = ftruncate(fd, size);
+  TEST_AND_RETURN_FALSE_ERRNO(return_code == 0);
+  return true;
+}
+
+static size_t GetSignatureSize(const string& private_key_path) {
+  const brillo::Blob data(1, 'x');
+  brillo::Blob hash;
+  EXPECT_TRUE(HashCalculator::RawHashOfData(data, &hash));
+  brillo::Blob signature;
+  EXPECT_TRUE(PayloadSigner::SignHash(hash,
+                                      private_key_path,
+                                      &signature));
+  return signature.size();
+}
+
+static bool InsertSignaturePlaceholder(int signature_size,
+                                       const string& payload_path,
+                                       uint64_t* out_metadata_size) {
+  vector<brillo::Blob> signatures;
+  signatures.push_back(brillo::Blob(signature_size, 0));
+
+  return PayloadSigner::AddSignatureToPayload(
+      payload_path,
+      signatures,
+      {},
+      payload_path,
+      out_metadata_size);
+}
+
+static void SignGeneratedPayload(const string& payload_path,
+                                 uint64_t* out_metadata_size) {
+  int signature_size = GetSignatureSize(kUnittestPrivateKeyPath);
+  brillo::Blob hash;
+  ASSERT_TRUE(PayloadSigner::HashPayloadForSigning(
+      payload_path,
+      vector<int>(1, signature_size),
+      &hash,
+      nullptr));
+  brillo::Blob signature;
+  ASSERT_TRUE(PayloadSigner::SignHash(hash,
+                                      kUnittestPrivateKeyPath,
+                                      &signature));
+  ASSERT_TRUE(PayloadSigner::AddSignatureToPayload(
+      payload_path,
+      vector<brillo::Blob>(1, signature),
+      {},
+      payload_path,
+      out_metadata_size));
+  EXPECT_TRUE(PayloadSigner::VerifySignedPayload(
+      payload_path,
+      kUnittestPublicKeyPath));
+}
+
+static void SignGeneratedShellPayload(SignatureTest signature_test,
+                                      const string& payload_path) {
+  string private_key_path = kUnittestPrivateKeyPath;
+  if (signature_test == kSignatureGeneratedShellBadKey) {
+    ASSERT_TRUE(utils::MakeTempFile("key.XXXXXX",
+                                    &private_key_path,
+                                    nullptr));
+  } else {
+    ASSERT_TRUE(signature_test == kSignatureGeneratedShell ||
+                signature_test == kSignatureGeneratedShellRotateCl1 ||
+                signature_test == kSignatureGeneratedShellRotateCl2);
+  }
+  ScopedPathUnlinker key_unlinker(private_key_path);
+  key_unlinker.set_should_remove(signature_test ==
+                                 kSignatureGeneratedShellBadKey);
+  // Generates a new private key that will not match the public key.
+  if (signature_test == kSignatureGeneratedShellBadKey) {
+    LOG(INFO) << "Generating a mismatched private key.";
+    ASSERT_EQ(0, System(base::StringPrintf(
+        "openssl genrsa -out %s 2048", private_key_path.c_str())));
+  }
+  int signature_size = GetSignatureSize(private_key_path);
+  string hash_file;
+  ASSERT_TRUE(utils::MakeTempFile("hash.XXXXXX", &hash_file, nullptr));
+  ScopedPathUnlinker hash_unlinker(hash_file);
+  string signature_size_string;
+  if (signature_test == kSignatureGeneratedShellRotateCl1 ||
+      signature_test == kSignatureGeneratedShellRotateCl2)
+    signature_size_string = base::StringPrintf("%d:%d",
+                                               signature_size, signature_size);
+  else
+    signature_size_string = base::StringPrintf("%d", signature_size);
+  ASSERT_EQ(0,
+            System(base::StringPrintf(
+                "./delta_generator -in_file=%s -signature_size=%s "
+                "-out_hash_file=%s",
+                payload_path.c_str(),
+                signature_size_string.c_str(),
+                hash_file.c_str())));
+
+  // Pad the hash
+  brillo::Blob hash;
+  ASSERT_TRUE(utils::ReadFile(hash_file, &hash));
+  ASSERT_TRUE(PayloadVerifier::PadRSA2048SHA256Hash(&hash));
+  ASSERT_TRUE(test_utils::WriteFileVector(hash_file, hash));
+
+  string sig_file;
+  ASSERT_TRUE(utils::MakeTempFile("signature.XXXXXX", &sig_file, nullptr));
+  ScopedPathUnlinker sig_unlinker(sig_file);
+  ASSERT_EQ(0,
+            System(base::StringPrintf(
+                "openssl rsautl -raw -sign -inkey %s -in %s -out %s",
+                private_key_path.c_str(),
+                hash_file.c_str(),
+                sig_file.c_str())));
+  string sig_file2;
+  ASSERT_TRUE(utils::MakeTempFile("signature.XXXXXX", &sig_file2, nullptr));
+  ScopedPathUnlinker sig2_unlinker(sig_file2);
+  if (signature_test == kSignatureGeneratedShellRotateCl1 ||
+      signature_test == kSignatureGeneratedShellRotateCl2) {
+    ASSERT_EQ(0,
+              System(base::StringPrintf(
+                  "openssl rsautl -raw -sign -inkey %s -in %s -out %s",
+                  kUnittestPrivateKey2Path,
+                  hash_file.c_str(),
+                  sig_file2.c_str())));
+    // Append second sig file to first path
+    sig_file += ":" + sig_file2;
+  }
+
+  ASSERT_EQ(0,
+            System(base::StringPrintf(
+                "./delta_generator -in_file=%s -signature_file=%s "
+                "-out_file=%s",
+                payload_path.c_str(),
+                sig_file.c_str(),
+                payload_path.c_str())));
+  int verify_result =
+      System(base::StringPrintf(
+          "./delta_generator -in_file=%s -public_key=%s -public_key_version=%d",
+          payload_path.c_str(),
+          signature_test == kSignatureGeneratedShellRotateCl2 ?
+          kUnittestPublicKey2Path : kUnittestPublicKeyPath,
+          signature_test == kSignatureGeneratedShellRotateCl2 ? 2 : 1));
+  if (signature_test == kSignatureGeneratedShellBadKey) {
+    ASSERT_NE(0, verify_result);
+  } else {
+    ASSERT_EQ(0, verify_result);
+  }
+}
+
+static void GenerateDeltaFile(bool full_kernel,
+                              bool full_rootfs,
+                              bool noop,
+                              ssize_t chunk_size,
+                              SignatureTest signature_test,
+                              DeltaState *state,
+                              uint32_t minor_version) {
+  EXPECT_TRUE(utils::MakeTempFile("a_img.XXXXXX", &state->a_img, nullptr));
+  EXPECT_TRUE(utils::MakeTempFile("b_img.XXXXXX", &state->b_img, nullptr));
+
+  // result_img is used in minor version 2. Instead of applying the update
+  // in-place on A, we apply it to a new image, result_img.
+  EXPECT_TRUE(
+      utils::MakeTempFile("result_img.XXXXXX", &state->result_img, nullptr));
+  test_utils::CreateExtImageAtPath(state->a_img, nullptr);
+
+  state->image_size = utils::FileSize(state->a_img);
+
+  // Create ImageInfo A & B
+  ImageInfo old_image_info;
+  ImageInfo new_image_info;
+
+  if (!full_rootfs) {
+    old_image_info.set_channel("src-channel");
+    old_image_info.set_board("src-board");
+    old_image_info.set_version("src-version");
+    old_image_info.set_key("src-key");
+    old_image_info.set_build_channel("src-build-channel");
+    old_image_info.set_build_version("src-build-version");
+  }
+
+  new_image_info.set_channel("test-channel");
+  new_image_info.set_board("test-board");
+  new_image_info.set_version("test-version");
+  new_image_info.set_key("test-key");
+  new_image_info.set_build_channel("test-build-channel");
+  new_image_info.set_build_version("test-build-version");
+
+  // Make some changes to the A image.
+  {
+    string a_mnt;
+    ScopedLoopMounter b_mounter(state->a_img, &a_mnt, 0);
+
+    brillo::Blob hardtocompress;
+    while (hardtocompress.size() < 3 * kBlockSize) {
+      hardtocompress.insert(hardtocompress.end(),
+                            std::begin(kRandomString), std::end(kRandomString));
+    }
+    EXPECT_TRUE(utils::WriteFile(base::StringPrintf("%s/hardtocompress",
+                                                    a_mnt.c_str()).c_str(),
+                                 hardtocompress.data(),
+                                 hardtocompress.size()));
+
+    brillo::Blob zeros(16 * 1024, 0);
+    EXPECT_EQ(zeros.size(),
+              base::WriteFile(base::FilePath(base::StringPrintf(
+                                  "%s/move-to-sparse", a_mnt.c_str())),
+                              reinterpret_cast<const char*>(zeros.data()),
+                              zeros.size()));
+
+    EXPECT_TRUE(
+        WriteSparseFile(base::StringPrintf("%s/move-from-sparse",
+                                           a_mnt.c_str()), 16 * 1024));
+
+    EXPECT_EQ(0,
+              System(base::StringPrintf("dd if=/dev/zero of=%s/move-semi-sparse"
+                                        " bs=1 seek=4096 count=1 status=none",
+                                        a_mnt.c_str()).c_str()));
+
+    // Write 1 MiB of 0xff to try to catch the case where writing a bsdiff
+    // patch fails to zero out the final block.
+    brillo::Blob ones(1024 * 1024, 0xff);
+    EXPECT_TRUE(utils::WriteFile(base::StringPrintf("%s/ones",
+                                                    a_mnt.c_str()).c_str(),
+                                 ones.data(),
+                                 ones.size()));
+  }
+
+  if (noop) {
+    EXPECT_TRUE(base::CopyFile(base::FilePath(state->a_img),
+                               base::FilePath(state->b_img)));
+    old_image_info = new_image_info;
+  } else {
+    if (minor_version == kSourceMinorPayloadVersion) {
+      // Create a result image with image_size bytes of garbage.
+      brillo::Blob ones(state->image_size, 0xff);
+      EXPECT_TRUE(utils::WriteFile(state->result_img.c_str(),
+                                   ones.data(),
+                                   ones.size()));
+      EXPECT_EQ(utils::FileSize(state->a_img),
+                utils::FileSize(state->result_img));
+    }
+
+    test_utils::CreateExtImageAtPath(state->b_img, nullptr);
+
+    // Make some changes to the B image.
+    string b_mnt;
+    ScopedLoopMounter b_mounter(state->b_img, &b_mnt, 0);
+
+    EXPECT_EQ(0, System(base::StringPrintf("cp %s/hello %s/hello2",
+                                           b_mnt.c_str(),
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(base::StringPrintf("rm %s/hello",
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(base::StringPrintf("mv %s/hello2 %s/hello",
+                                           b_mnt.c_str(),
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(base::StringPrintf("echo foo > %s/foo",
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(base::StringPrintf("touch %s/emptyfile",
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_TRUE(WriteSparseFile(base::StringPrintf("%s/fullsparse",
+                                                   b_mnt.c_str()),
+                                                   1024 * 1024));
+
+    EXPECT_TRUE(
+        WriteSparseFile(base::StringPrintf("%s/move-to-sparse", b_mnt.c_str()),
+                        16 * 1024));
+
+    brillo::Blob zeros(16 * 1024, 0);
+    EXPECT_EQ(zeros.size(),
+              base::WriteFile(base::FilePath(base::StringPrintf(
+                                  "%s/move-from-sparse", b_mnt.c_str())),
+                              reinterpret_cast<const char*>(zeros.data()),
+                              zeros.size()));
+
+    EXPECT_EQ(0, System(base::StringPrintf("dd if=/dev/zero "
+                                           "of=%s/move-semi-sparse "
+                                           "bs=1 seek=4096 count=1 status=none",
+                                           b_mnt.c_str()).c_str()));
+
+    EXPECT_EQ(0, System(base::StringPrintf("dd if=/dev/zero "
+                                           "of=%s/partsparse bs=1 "
+                                           "seek=4096 count=1 status=none",
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(base::StringPrintf("cp %s/srchardlink0 %s/tmp && "
+                                           "mv %s/tmp %s/srchardlink1",
+                                           b_mnt.c_str(),
+                                           b_mnt.c_str(),
+                                           b_mnt.c_str(),
+                                           b_mnt.c_str()).c_str()));
+    EXPECT_EQ(0, System(
+        base::StringPrintf("rm %s/boguslink && echo foobar > %s/boguslink",
+                           b_mnt.c_str(), b_mnt.c_str()).c_str()));
+
+    brillo::Blob hardtocompress;
+    while (hardtocompress.size() < 3 * kBlockSize) {
+      hardtocompress.insert(hardtocompress.end(),
+                            std::begin(kRandomString), std::end(kRandomString));
+    }
+    EXPECT_TRUE(utils::WriteFile(base::StringPrintf("%s/hardtocompress",
+                                              b_mnt.c_str()).c_str(),
+                                 hardtocompress.data(),
+                                 hardtocompress.size()));
+  }
+
+  string old_kernel;
+  EXPECT_TRUE(utils::MakeTempFile("old_kernel.XXXXXX",
+                                  &state->old_kernel,
+                                  nullptr));
+
+  string new_kernel;
+  EXPECT_TRUE(utils::MakeTempFile("new_kernel.XXXXXX",
+                                  &state->new_kernel,
+                                  nullptr));
+
+  string result_kernel;
+  EXPECT_TRUE(utils::MakeTempFile("result_kernel.XXXXXX",
+                                  &state->result_kernel,
+                                  nullptr));
+
+  state->kernel_size = kDefaultKernelSize;
+  state->old_kernel_data.resize(kDefaultKernelSize);
+  state->new_kernel_data.resize(state->old_kernel_data.size());
+  state->result_kernel_data.resize(state->old_kernel_data.size());
+  test_utils::FillWithData(&state->old_kernel_data);
+  test_utils::FillWithData(&state->new_kernel_data);
+  test_utils::FillWithData(&state->result_kernel_data);
+
+  // change the new kernel data
+  std::copy(std::begin(kNewData), std::end(kNewData),
+            state->new_kernel_data.begin());
+
+  if (noop) {
+    state->old_kernel_data = state->new_kernel_data;
+  }
+
+  // Write kernels to disk
+  EXPECT_TRUE(utils::WriteFile(state->old_kernel.c_str(),
+                               state->old_kernel_data.data(),
+                               state->old_kernel_data.size()));
+  EXPECT_TRUE(utils::WriteFile(state->new_kernel.c_str(),
+                               state->new_kernel_data.data(),
+                               state->new_kernel_data.size()));
+  EXPECT_TRUE(utils::WriteFile(state->result_kernel.c_str(),
+                               state->result_kernel_data.data(),
+                               state->result_kernel_data.size()));
+
+  EXPECT_TRUE(utils::MakeTempFile("delta.XXXXXX",
+                                  &state->delta_path,
+                                  nullptr));
+  LOG(INFO) << "delta path: " << state->delta_path;
+  {
+    const string private_key =
+        signature_test == kSignatureGenerator ? kUnittestPrivateKeyPath : "";
+
+    PayloadGenerationConfig payload_config;
+    payload_config.is_delta = !full_rootfs;
+    payload_config.hard_chunk_size = chunk_size;
+    payload_config.rootfs_partition_size = kRootFSPartitionSize;
+    payload_config.major_version = kChromeOSMajorPayloadVersion;
+    payload_config.minor_version = minor_version;
+    if (!full_rootfs) {
+      payload_config.source.partitions.emplace_back(kLegacyPartitionNameRoot);
+      payload_config.source.partitions.emplace_back(kLegacyPartitionNameKernel);
+      payload_config.source.partitions.front().path = state->a_img;
+      if (!full_kernel)
+        payload_config.source.partitions.back().path = state->old_kernel;
+      payload_config.source.image_info = old_image_info;
+      EXPECT_TRUE(payload_config.source.LoadImageSize());
+      for (PartitionConfig& part : payload_config.source.partitions)
+        EXPECT_TRUE(part.OpenFilesystem());
+    } else {
+      if (payload_config.hard_chunk_size == -1)
+        // Use 1 MiB chunk size for the full unittests.
+        payload_config.hard_chunk_size = 1024 * 1024;
+    }
+    payload_config.target.partitions.emplace_back(kLegacyPartitionNameRoot);
+    payload_config.target.partitions.back().path = state->b_img;
+    payload_config.target.partitions.emplace_back(kLegacyPartitionNameKernel);
+    payload_config.target.partitions.back().path = state->new_kernel;
+    payload_config.target.image_info = new_image_info;
+    EXPECT_TRUE(payload_config.target.LoadImageSize());
+    for (PartitionConfig& part : payload_config.target.partitions)
+      EXPECT_TRUE(part.OpenFilesystem());
+
+    EXPECT_TRUE(payload_config.Validate());
+    EXPECT_TRUE(
+        GenerateUpdatePayloadFile(
+            payload_config,
+            state->delta_path,
+            private_key,
+            &state->metadata_size));
+  }
+  // Extend the "partitions" holding the file system a bit.
+  EXPECT_EQ(0, HANDLE_EINTR(truncate(state->a_img.c_str(),
+                                     state->image_size + 1024 * 1024)));
+  EXPECT_EQ(state->image_size + 1024 * 1024, utils::FileSize(state->a_img));
+  EXPECT_EQ(0, HANDLE_EINTR(truncate(state->b_img.c_str(),
+                                     state->image_size + 1024 * 1024)));
+  EXPECT_EQ(state->image_size + 1024 * 1024, utils::FileSize(state->b_img));
+
+  if (signature_test == kSignatureGeneratedPlaceholder ||
+      signature_test == kSignatureGeneratedPlaceholderMismatch) {
+    int signature_size = GetSignatureSize(kUnittestPrivateKeyPath);
+    LOG(INFO) << "Inserting placeholder signature.";
+    ASSERT_TRUE(InsertSignaturePlaceholder(signature_size, state->delta_path,
+                                           &state->metadata_size));
+
+    if (signature_test == kSignatureGeneratedPlaceholderMismatch) {
+      signature_size -= 1;
+      LOG(INFO) << "Inserting mismatched placeholder signature.";
+      ASSERT_FALSE(InsertSignaturePlaceholder(signature_size, state->delta_path,
+                                              &state->metadata_size));
+      return;
+    }
+  }
+
+  if (signature_test == kSignatureGenerated ||
+      signature_test == kSignatureGeneratedPlaceholder ||
+      signature_test == kSignatureGeneratedPlaceholderMismatch) {
+    // Generate the signed payload and update the metadata size in state to
+    // reflect the new size after adding the signature operation to the
+    // manifest.
+    LOG(INFO) << "Signing payload.";
+    SignGeneratedPayload(state->delta_path, &state->metadata_size);
+  } else if (signature_test == kSignatureGeneratedShell ||
+             signature_test == kSignatureGeneratedShellBadKey ||
+             signature_test == kSignatureGeneratedShellRotateCl1 ||
+             signature_test == kSignatureGeneratedShellRotateCl2) {
+    SignGeneratedShellPayload(signature_test, state->delta_path);
+  }
+}
+
+static void ApplyDeltaFile(bool full_kernel, bool full_rootfs, bool noop,
+                           SignatureTest signature_test, DeltaState* state,
+                           bool hash_checks_mandatory,
+                           OperationHashTest op_hash_test,
+                           DeltaPerformer** performer,
+                           uint32_t minor_version) {
+  // Check the metadata.
+  {
+    DeltaArchiveManifest manifest;
+    EXPECT_TRUE(PayloadSigner::LoadPayload(state->delta_path,
+                                           &state->delta,
+                                           &manifest,
+                                           nullptr,
+                                           &state->metadata_size,
+                                           nullptr));
+    LOG(INFO) << "Metadata size: " << state->metadata_size;
+
+    if (signature_test == kSignatureNone) {
+      EXPECT_FALSE(manifest.has_signatures_offset());
+      EXPECT_FALSE(manifest.has_signatures_size());
+    } else {
+      EXPECT_TRUE(manifest.has_signatures_offset());
+      EXPECT_TRUE(manifest.has_signatures_size());
+      Signatures sigs_message;
+      EXPECT_TRUE(sigs_message.ParseFromArray(
+          &state->delta[state->metadata_size + manifest.signatures_offset()],
+          manifest.signatures_size()));
+      if (signature_test == kSignatureGeneratedShellRotateCl1 ||
+          signature_test == kSignatureGeneratedShellRotateCl2)
+        EXPECT_EQ(2, sigs_message.signatures_size());
+      else
+        EXPECT_EQ(1, sigs_message.signatures_size());
+      const Signatures_Signature& signature = sigs_message.signatures(0);
+      EXPECT_EQ(1, signature.version());
+
+      uint64_t expected_sig_data_length = 0;
+      vector<string> key_paths{kUnittestPrivateKeyPath};
+      if (signature_test == kSignatureGeneratedShellRotateCl1 ||
+          signature_test == kSignatureGeneratedShellRotateCl2) {
+        key_paths.push_back(kUnittestPrivateKey2Path);
+      }
+      EXPECT_TRUE(PayloadSigner::SignatureBlobLength(
+          key_paths,
+          &expected_sig_data_length));
+      EXPECT_EQ(expected_sig_data_length, manifest.signatures_size());
+      EXPECT_FALSE(signature.data().empty());
+    }
+
+    if (noop) {
+      EXPECT_EQ(0, manifest.install_operations_size());
+      EXPECT_EQ(1, manifest.kernel_install_operations_size());
+    }
+
+    if (full_kernel) {
+      EXPECT_FALSE(manifest.has_old_kernel_info());
+    } else {
+      EXPECT_EQ(state->old_kernel_data.size(),
+                manifest.old_kernel_info().size());
+      EXPECT_FALSE(manifest.old_kernel_info().hash().empty());
+    }
+
+    EXPECT_EQ(manifest.new_image_info().channel(), "test-channel");
+    EXPECT_EQ(manifest.new_image_info().board(), "test-board");
+    EXPECT_EQ(manifest.new_image_info().version(), "test-version");
+    EXPECT_EQ(manifest.new_image_info().key(), "test-key");
+    EXPECT_EQ(manifest.new_image_info().build_channel(), "test-build-channel");
+    EXPECT_EQ(manifest.new_image_info().build_version(), "test-build-version");
+
+    if (!full_rootfs) {
+      if (noop) {
+        EXPECT_EQ(manifest.old_image_info().channel(), "test-channel");
+        EXPECT_EQ(manifest.old_image_info().board(), "test-board");
+        EXPECT_EQ(manifest.old_image_info().version(), "test-version");
+        EXPECT_EQ(manifest.old_image_info().key(), "test-key");
+        EXPECT_EQ(manifest.old_image_info().build_channel(),
+                  "test-build-channel");
+        EXPECT_EQ(manifest.old_image_info().build_version(),
+                  "test-build-version");
+      } else {
+        EXPECT_EQ(manifest.old_image_info().channel(), "src-channel");
+        EXPECT_EQ(manifest.old_image_info().board(), "src-board");
+        EXPECT_EQ(manifest.old_image_info().version(), "src-version");
+        EXPECT_EQ(manifest.old_image_info().key(), "src-key");
+        EXPECT_EQ(manifest.old_image_info().build_channel(),
+                  "src-build-channel");
+        EXPECT_EQ(manifest.old_image_info().build_version(),
+                  "src-build-version");
+      }
+    }
+
+
+    if (full_rootfs) {
+      EXPECT_FALSE(manifest.has_old_rootfs_info());
+      EXPECT_FALSE(manifest.has_old_image_info());
+      EXPECT_TRUE(manifest.has_new_image_info());
+    } else {
+      EXPECT_EQ(state->image_size, manifest.old_rootfs_info().size());
+      EXPECT_FALSE(manifest.old_rootfs_info().hash().empty());
+    }
+
+    EXPECT_EQ(state->new_kernel_data.size(), manifest.new_kernel_info().size());
+    EXPECT_EQ(state->image_size, manifest.new_rootfs_info().size());
+
+    EXPECT_FALSE(manifest.new_kernel_info().hash().empty());
+    EXPECT_FALSE(manifest.new_rootfs_info().hash().empty());
+  }
+
+  MockPrefs prefs;
+  EXPECT_CALL(prefs, SetInt64(kPrefsManifestMetadataSize,
+                              state->metadata_size)).WillOnce(Return(true));
+  EXPECT_CALL(prefs, SetInt64(kPrefsUpdateStateNextOperation, _))
+      .WillRepeatedly(Return(true));
+  EXPECT_CALL(prefs, GetInt64(kPrefsUpdateStateNextOperation, _))
+      .WillOnce(Return(false));
+  EXPECT_CALL(prefs, SetInt64(kPrefsUpdateStateNextDataOffset, _))
+      .WillRepeatedly(Return(true));
+  EXPECT_CALL(prefs, SetInt64(kPrefsUpdateStateNextDataLength, _))
+      .WillRepeatedly(Return(true));
+  EXPECT_CALL(prefs, SetString(kPrefsUpdateStateSHA256Context, _))
+      .WillRepeatedly(Return(true));
+  EXPECT_CALL(prefs, SetString(kPrefsUpdateStateSignedSHA256Context, _))
+      .WillRepeatedly(Return(true));
+  if (op_hash_test == kValidOperationData && signature_test != kSignatureNone) {
+    EXPECT_CALL(prefs, SetString(kPrefsUpdateStateSignatureBlob, _))
+        .WillOnce(Return(true));
+  }
+
+  EXPECT_CALL(state->mock_delegate_, ShouldCancel(_))
+      .WillRepeatedly(Return(false));
+
+  // Update the A image in place.
+  InstallPlan* install_plan = &state->install_plan;
+  install_plan->hash_checks_mandatory = hash_checks_mandatory;
+  install_plan->metadata_size = state->metadata_size;
+  install_plan->is_full_update = full_kernel && full_rootfs;
+  install_plan->source_slot = 0;
+  install_plan->target_slot = 1;
+
+  InstallPlan::Partition root_part;
+  root_part.name = kLegacyPartitionNameRoot;
+
+  InstallPlan::Partition kernel_part;
+  kernel_part.name = kLegacyPartitionNameKernel;
+
+  LOG(INFO) << "Setting payload metadata size in Omaha  = "
+            << state->metadata_size;
+  ASSERT_TRUE(PayloadSigner::GetMetadataSignature(
+      state->delta.data(),
+      state->metadata_size,
+      kUnittestPrivateKeyPath,
+      &install_plan->metadata_signature));
+  EXPECT_FALSE(install_plan->metadata_signature.empty());
+
+  *performer = new DeltaPerformer(&prefs,
+                                  &state->fake_boot_control_,
+                                  &state->fake_hardware_,
+                                  &state->mock_delegate_,
+                                  install_plan);
+  EXPECT_TRUE(utils::FileExists(kUnittestPublicKeyPath));
+  (*performer)->set_public_key_path(kUnittestPublicKeyPath);
+  DeltaPerformerIntegrationTest::SetSupportedVersion(*performer, minor_version);
+
+  EXPECT_EQ(state->image_size,
+            HashCalculator::RawHashOfFile(
+                state->a_img,
+                state->image_size,
+                &root_part.source_hash));
+  EXPECT_TRUE(HashCalculator::RawHashOfData(
+                  state->old_kernel_data,
+                  &kernel_part.source_hash));
+
+  // This partitions are normally filed by the FilesystemVerifierAction with
+  // the source hashes used for deltas.
+  install_plan->partitions = {root_part, kernel_part};
+
+  // With minor version 2, we want the target to be the new image, result_img,
+  // but with version 1, we want to update A in place.
+  string target_root, target_kernel;
+  if (minor_version == kSourceMinorPayloadVersion) {
+    target_root = state->result_img;
+    target_kernel = state->result_kernel;
+  } else {
+    target_root = state->a_img;
+    target_kernel = state->old_kernel;
+  }
+
+  state->fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameRoot, install_plan->source_slot, state->a_img);
+  state->fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameKernel, install_plan->source_slot, state->old_kernel);
+  state->fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameRoot, install_plan->target_slot, target_root);
+  state->fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameKernel, install_plan->target_slot, target_kernel);
+
+  ErrorCode expected_error, actual_error;
+  bool continue_writing;
+  switch (op_hash_test) {
+    case kInvalidOperationData: {
+      // Muck with some random offset post the metadata size so that
+      // some operation hash will result in a mismatch.
+      int some_offset = state->metadata_size + 300;
+      LOG(INFO) << "Tampered value at offset: " << some_offset;
+      state->delta[some_offset]++;
+      expected_error = ErrorCode::kDownloadOperationHashMismatch;
+      continue_writing = false;
+      break;
+    }
+
+    case kValidOperationData:
+    default:
+      // no change.
+      expected_error = ErrorCode::kSuccess;
+      continue_writing = true;
+      break;
+  }
+
+  // Write at some number of bytes per operation. Arbitrarily chose 5.
+  const size_t kBytesPerWrite = 5;
+  for (size_t i = 0; i < state->delta.size(); i += kBytesPerWrite) {
+    size_t count = std::min(state->delta.size() - i, kBytesPerWrite);
+    bool write_succeeded = ((*performer)->Write(&state->delta[i],
+                                                count,
+                                                &actual_error));
+    // Normally write_succeeded should be true every time and
+    // actual_error should be ErrorCode::kSuccess. If so, continue the loop.
+    // But if we seeded an operation hash error above, then write_succeeded
+    // will be false. The failure may happen at any operation n. So, all
+    // Writes until n-1 should succeed and the nth operation will fail with
+    // actual_error. In this case, we should bail out of the loop because
+    // we cannot proceed applying the delta.
+    if (!write_succeeded) {
+      LOG(INFO) << "Write failed. Checking if it failed with expected error";
+      EXPECT_EQ(expected_error, actual_error);
+      if (!continue_writing) {
+        LOG(INFO) << "Cannot continue writing. Bailing out.";
+        break;
+      }
+    }
+
+    EXPECT_EQ(ErrorCode::kSuccess, actual_error);
+  }
+
+  // If we had continued all the way through, Close should succeed.
+  // Otherwise, it should fail. Check appropriately.
+  bool close_result = (*performer)->Close();
+  if (continue_writing)
+    EXPECT_EQ(0, close_result);
+  else
+    EXPECT_LE(0, close_result);
+}
+
+void VerifyPayloadResult(DeltaPerformer* performer,
+                         DeltaState* state,
+                         ErrorCode expected_result,
+                         uint32_t minor_version) {
+  if (!performer) {
+    EXPECT_TRUE(!"Skipping payload verification since performer is null.");
+    return;
+  }
+
+  int expected_times = (expected_result == ErrorCode::kSuccess) ? 1 : 0;
+  EXPECT_CALL(state->mock_delegate_, DownloadComplete()).Times(expected_times);
+
+  LOG(INFO) << "Verifying payload for expected result "
+            << expected_result;
+  EXPECT_EQ(expected_result, performer->VerifyPayload(
+      HashCalculator::HashOfData(state->delta),
+      state->delta.size()));
+  LOG(INFO) << "Verified payload.";
+
+  if (expected_result != ErrorCode::kSuccess) {
+    // no need to verify new partition if VerifyPayload failed.
+    return;
+  }
+
+  brillo::Blob updated_kernel_partition;
+  if (minor_version == kSourceMinorPayloadVersion) {
+    CompareFilesByBlock(state->result_kernel, state->new_kernel,
+                        state->kernel_size);
+    CompareFilesByBlock(state->result_img, state->b_img,
+                        state->image_size);
+    EXPECT_TRUE(utils::ReadFile(state->result_kernel,
+                                &updated_kernel_partition));
+  } else {
+    CompareFilesByBlock(state->old_kernel, state->new_kernel,
+                        state->kernel_size);
+    CompareFilesByBlock(state->a_img, state->b_img,
+                        state->image_size);
+    EXPECT_TRUE(utils::ReadFile(state->old_kernel, &updated_kernel_partition));
+  }
+
+  ASSERT_GE(updated_kernel_partition.size(), arraysize(kNewData));
+  EXPECT_TRUE(std::equal(std::begin(kNewData), std::end(kNewData),
+                         updated_kernel_partition.begin()));
+
+  const auto& partitions = state->install_plan.partitions;
+  EXPECT_EQ(2, partitions.size());
+  EXPECT_EQ(kLegacyPartitionNameRoot, partitions[0].name);
+  EXPECT_EQ(kLegacyPartitionNameKernel, partitions[1].name);
+
+  EXPECT_EQ(kDefaultKernelSize, partitions[1].target_size);
+  brillo::Blob expected_new_kernel_hash;
+  EXPECT_TRUE(HashCalculator::RawHashOfData(state->new_kernel_data,
+                                            &expected_new_kernel_hash));
+  EXPECT_EQ(expected_new_kernel_hash, partitions[1].target_hash);
+
+  EXPECT_EQ(state->image_size, partitions[0].target_size);
+  brillo::Blob expected_new_rootfs_hash;
+  EXPECT_EQ(state->image_size,
+            HashCalculator::RawHashOfFile(state->b_img,
+                                          state->image_size,
+                                          &expected_new_rootfs_hash));
+  EXPECT_EQ(expected_new_rootfs_hash, partitions[0].target_hash);
+}
+
+void VerifyPayload(DeltaPerformer* performer,
+                   DeltaState* state,
+                   SignatureTest signature_test,
+                   uint32_t minor_version) {
+  ErrorCode expected_result = ErrorCode::kSuccess;
+  switch (signature_test) {
+    case kSignatureNone:
+      expected_result = ErrorCode::kSignedDeltaPayloadExpectedError;
+      break;
+    case kSignatureGeneratedShellBadKey:
+      expected_result = ErrorCode::kDownloadPayloadPubKeyVerificationError;
+      break;
+    default: break;  // appease gcc
+  }
+
+  VerifyPayloadResult(performer, state, expected_result, minor_version);
+}
+
+void DoSmallImageTest(bool full_kernel, bool full_rootfs, bool noop,
+                      ssize_t chunk_size,
+                      SignatureTest signature_test,
+                      bool hash_checks_mandatory, uint32_t minor_version) {
+  DeltaState state;
+  DeltaPerformer *performer = nullptr;
+  GenerateDeltaFile(full_kernel, full_rootfs, noop, chunk_size,
+                    signature_test, &state, minor_version);
+
+  ScopedPathUnlinker a_img_unlinker(state.a_img);
+  ScopedPathUnlinker b_img_unlinker(state.b_img);
+  ScopedPathUnlinker new_img_unlinker(state.result_img);
+  ScopedPathUnlinker delta_unlinker(state.delta_path);
+  ScopedPathUnlinker old_kernel_unlinker(state.old_kernel);
+  ScopedPathUnlinker new_kernel_unlinker(state.new_kernel);
+  ScopedPathUnlinker result_kernel_unlinker(state.result_kernel);
+  ApplyDeltaFile(full_kernel, full_rootfs, noop, signature_test,
+                 &state, hash_checks_mandatory, kValidOperationData,
+                 &performer, minor_version);
+  VerifyPayload(performer, &state, signature_test, minor_version);
+  delete performer;
+}
+
+void DoOperationHashMismatchTest(OperationHashTest op_hash_test,
+                                 bool hash_checks_mandatory) {
+  DeltaState state;
+  uint64_t minor_version = kFullPayloadMinorVersion;
+  GenerateDeltaFile(true, true, false, -1, kSignatureGenerated, &state,
+                    minor_version);
+  ScopedPathUnlinker a_img_unlinker(state.a_img);
+  ScopedPathUnlinker b_img_unlinker(state.b_img);
+  ScopedPathUnlinker delta_unlinker(state.delta_path);
+  ScopedPathUnlinker old_kernel_unlinker(state.old_kernel);
+  ScopedPathUnlinker new_kernel_unlinker(state.new_kernel);
+  DeltaPerformer *performer = nullptr;
+  ApplyDeltaFile(true, true, false, kSignatureGenerated, &state,
+                 hash_checks_mandatory, op_hash_test, &performer,
+                 minor_version);
+  delete performer;
+}
+
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGenerator,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignaturePlaceholderTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGeneratedPlaceholder,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignaturePlaceholderMismatchTest) {
+  DeltaState state;
+  GenerateDeltaFile(false, false, false, -1,
+                    kSignatureGeneratedPlaceholderMismatch, &state,
+                    kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageChunksTest) {
+  DoSmallImageTest(false, false, false, kBlockSize, kSignatureGenerator,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootFullKernelSmallImageTest) {
+  DoSmallImageTest(true, false, false, -1, kSignatureGenerator,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootFullSmallImageTest) {
+  DoSmallImageTest(true, true, false, -1, kSignatureGenerator,
+                   true, kFullPayloadMinorVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootNoopSmallImageTest) {
+  DoSmallImageTest(false, false, true, -1, kSignatureGenerator,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignNoneTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureNone,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignGeneratedTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGenerated,
+                   true, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignGeneratedShellTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGeneratedShell,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignGeneratedShellBadKeyTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGeneratedShellBadKey,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignGeneratedShellRotateCl1Test) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGeneratedShellRotateCl1,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSignGeneratedShellRotateCl2Test) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGeneratedShellRotateCl2,
+                   false, kInPlaceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootSmallImageSourceOpsTest) {
+  DoSmallImageTest(false, false, false, -1, kSignatureGenerator,
+                   false, kSourceMinorPayloadVersion);
+}
+
+TEST(DeltaPerformerIntegrationTest, RunAsRootMandatoryOperationHashMismatchTest) {
+  DoOperationHashMismatchTest(kInvalidOperationData, true);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/delta_performer_unittest.cc b/payload_consumer/delta_performer_unittest.cc
new file mode 100644
index 0000000..8192632
--- /dev/null
+++ b/payload_consumer/delta_performer_unittest.cc
@@ -0,0 +1,788 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/delta_performer.h"
+
+#include <inttypes.h>
+
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <gmock/gmock.h>
+#include <google/protobuf/repeated_field.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/mock_download_action.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/bzip.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/payload_file.h"
+#include "update_engine/payload_generator/payload_signer.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+using std::string;
+using std::vector;
+using test_utils::System;
+using test_utils::kRandomString;
+using testing::_;
+
+extern const char* kUnittestPrivateKeyPath;
+extern const char* kUnittestPublicKeyPath;
+
+static const char* kBogusMetadataSignature1 =
+    "awSFIUdUZz2VWFiR+ku0Pj00V7bPQPQFYQSXjEXr3vaw3TE4xHV5CraY3/YrZpBv"
+    "J5z4dSBskoeuaO1TNC/S6E05t+yt36tE4Fh79tMnJ/z9fogBDXWgXLEUyG78IEQr"
+    "YH6/eBsQGT2RJtBgXIXbZ9W+5G9KmGDoPOoiaeNsDuqHiBc/58OFsrxskH8E6vMS"
+    "BmMGGk82mvgzic7ApcoURbCGey1b3Mwne/hPZ/bb9CIyky8Og9IfFMdL2uAweOIR"
+    "fjoTeLYZpt+WN65Vu7jJ0cQN8e1y+2yka5112wpRf/LLtPgiAjEZnsoYpLUd7CoV"
+    "pLRtClp97kN2+tXGNBQqkA==";
+
+namespace {
+// Different options that determine what we should fill into the
+// install_plan.metadata_signature to simulate the contents received in the
+// Omaha response.
+enum MetadataSignatureTest {
+  kEmptyMetadataSignature,
+  kInvalidMetadataSignature,
+  kValidMetadataSignature,
+};
+
+// Compressed data without checksum, generated with:
+// echo -n a | xz -9 --check=none | hexdump -v -e '"    " 12/1 "0x%02x, " "\n"'
+const uint8_t kXzCompressedData[] = {
+    0xfd, 0x37, 0x7a, 0x58, 0x5a, 0x00, 0x00, 0x00, 0xff, 0x12, 0xd9, 0x41,
+    0x02, 0x00, 0x21, 0x01, 0x1c, 0x00, 0x00, 0x00, 0x10, 0xcf, 0x58, 0xcc,
+    0x01, 0x00, 0x00, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x11, 0x01,
+    0xad, 0xa6, 0x58, 0x04, 0x06, 0x72, 0x9e, 0x7a, 0x01, 0x00, 0x00, 0x00,
+    0x00, 0x00, 0x59, 0x5a,
+};
+
+}  // namespace
+
+class DeltaPerformerTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    install_plan_.source_slot = 0;
+    install_plan_.target_slot = 1;
+    EXPECT_CALL(mock_delegate_, ShouldCancel(_))
+        .WillRepeatedly(testing::Return(false));
+  }
+
+  // Test helper placed where it can easily be friended from DeltaPerformer.
+  void RunManifestValidation(const DeltaArchiveManifest& manifest,
+                             uint64_t major_version,
+                             bool full_payload,
+                             ErrorCode expected) {
+    // The install plan is for Full or Delta.
+    install_plan_.is_full_update = full_payload;
+
+    // The Manifest we are validating.
+    performer_.manifest_.CopyFrom(manifest);
+    performer_.major_payload_version_ = major_version;
+
+    EXPECT_EQ(expected, performer_.ValidateManifest());
+  }
+
+  brillo::Blob GeneratePayload(const brillo::Blob& blob_data,
+                               const vector<AnnotatedOperation>& aops,
+                               bool sign_payload) {
+    return GeneratePayload(blob_data, aops, sign_payload,
+                           DeltaPerformer::kSupportedMajorPayloadVersion,
+                           DeltaPerformer::kSupportedMinorPayloadVersion);
+  }
+
+  brillo::Blob GeneratePayload(const brillo::Blob& blob_data,
+                               const vector<AnnotatedOperation>& aops,
+                               bool sign_payload,
+                               uint64_t major_version,
+                               uint32_t minor_version) {
+    string blob_path;
+    EXPECT_TRUE(utils::MakeTempFile("Blob-XXXXXX", &blob_path, nullptr));
+    ScopedPathUnlinker blob_unlinker(blob_path);
+    EXPECT_TRUE(utils::WriteFile(blob_path.c_str(),
+                                 blob_data.data(),
+                                 blob_data.size()));
+
+    PayloadGenerationConfig config;
+    config.major_version = major_version;
+    config.minor_version = minor_version;
+
+    PayloadFile payload;
+    EXPECT_TRUE(payload.Init(config));
+
+    PartitionConfig old_part(kLegacyPartitionNameRoot);
+    PartitionConfig new_part(kLegacyPartitionNameRoot);
+    new_part.path = "/dev/zero";
+    new_part.size = 1234;
+
+    payload.AddPartition(old_part, new_part, aops);
+
+    // We include a kernel partition without operations.
+    old_part.name = kLegacyPartitionNameKernel;
+    new_part.name = kLegacyPartitionNameKernel;
+    new_part.size = 0;
+    payload.AddPartition(old_part, new_part, {});
+
+    string payload_path;
+    EXPECT_TRUE(utils::MakeTempFile("Payload-XXXXXX", &payload_path, nullptr));
+    ScopedPathUnlinker payload_unlinker(payload_path);
+    EXPECT_TRUE(payload.WritePayload(payload_path, blob_path,
+        sign_payload ? kUnittestPrivateKeyPath : "",
+        &install_plan_.metadata_size));
+
+    brillo::Blob payload_data;
+    EXPECT_TRUE(utils::ReadFile(payload_path, &payload_data));
+    return payload_data;
+  }
+
+  // Apply |payload_data| on partition specified in |source_path|.
+  // Expect result of performer_.Write() to be |expect_success|.
+  // Returns the result of the payload application.
+  brillo::Blob ApplyPayload(const brillo::Blob& payload_data,
+                            const string& source_path,
+                            bool expect_success) {
+    return ApplyPayloadToData(payload_data, source_path, brillo::Blob(),
+                              expect_success);
+  }
+
+  // Apply the payload provided in |payload_data| reading from the |source_path|
+  // file and writing the contents to a new partition. The existing data in the
+  // new target file are set to |target_data| before applying the payload.
+  // Expect result of performer_.Write() to be |expect_success|.
+  // Returns the result of the payload application.
+  brillo::Blob ApplyPayloadToData(const brillo::Blob& payload_data,
+                                  const string& source_path,
+                                  const brillo::Blob& target_data,
+                                  bool expect_success) {
+    string new_part;
+    EXPECT_TRUE(utils::MakeTempFile("Partition-XXXXXX", &new_part, nullptr));
+    ScopedPathUnlinker partition_unlinker(new_part);
+    EXPECT_TRUE(utils::WriteFile(new_part.c_str(), target_data.data(),
+                                 target_data.size()));
+
+    // We installed the operations only in the rootfs partition, but the
+    // delta performer needs to access all the partitions.
+    fake_boot_control_.SetPartitionDevice(
+        kLegacyPartitionNameRoot, install_plan_.target_slot, new_part);
+    fake_boot_control_.SetPartitionDevice(
+        kLegacyPartitionNameRoot, install_plan_.source_slot, source_path);
+    fake_boot_control_.SetPartitionDevice(
+        kLegacyPartitionNameKernel, install_plan_.target_slot, "/dev/null");
+    fake_boot_control_.SetPartitionDevice(
+        kLegacyPartitionNameKernel, install_plan_.source_slot, "/dev/null");
+
+    EXPECT_EQ(expect_success,
+              performer_.Write(payload_data.data(), payload_data.size()));
+    EXPECT_EQ(0, performer_.Close());
+
+    brillo::Blob partition_data;
+    EXPECT_TRUE(utils::ReadFile(new_part, &partition_data));
+    return partition_data;
+  }
+
+  // Calls delta performer's Write method by pretending to pass in bytes from a
+  // delta file whose metadata size is actual_metadata_size and tests if all
+  // checks are correctly performed if the install plan contains
+  // expected_metadata_size and that the result of the parsing are as per
+  // hash_checks_mandatory flag.
+  void DoMetadataSizeTest(uint64_t expected_metadata_size,
+                          uint64_t actual_metadata_size,
+                          bool hash_checks_mandatory) {
+    install_plan_.hash_checks_mandatory = hash_checks_mandatory;
+
+    // Set a valid magic string and version number 1.
+    EXPECT_TRUE(performer_.Write("CrAU", 4));
+    uint64_t version = htobe64(kChromeOSMajorPayloadVersion);
+    EXPECT_TRUE(performer_.Write(&version, 8));
+
+    install_plan_.metadata_size = expected_metadata_size;
+    ErrorCode error_code;
+    // When filling in size in manifest, exclude the size of the 20-byte header.
+    uint64_t size_in_manifest = htobe64(actual_metadata_size - 20);
+    bool result = performer_.Write(&size_in_manifest, 8, &error_code);
+    if (expected_metadata_size == actual_metadata_size ||
+        !hash_checks_mandatory) {
+      EXPECT_TRUE(result);
+    } else {
+      EXPECT_FALSE(result);
+      EXPECT_EQ(ErrorCode::kDownloadInvalidMetadataSize, error_code);
+    }
+
+    EXPECT_LT(performer_.Close(), 0);
+  }
+
+  // Generates a valid delta file but tests the delta performer by suppling
+  // different metadata signatures as per metadata_signature_test flag and
+  // sees if the result of the parsing are as per hash_checks_mandatory flag.
+  void DoMetadataSignatureTest(MetadataSignatureTest metadata_signature_test,
+                               bool sign_payload,
+                               bool hash_checks_mandatory) {
+
+    // Loads the payload and parses the manifest.
+    brillo::Blob payload = GeneratePayload(brillo::Blob(),
+        vector<AnnotatedOperation>(), sign_payload,
+        kChromeOSMajorPayloadVersion, kFullPayloadMinorVersion);
+
+    LOG(INFO) << "Payload size: " << payload.size();
+
+    install_plan_.hash_checks_mandatory = hash_checks_mandatory;
+
+    DeltaPerformer::MetadataParseResult expected_result, actual_result;
+    ErrorCode expected_error, actual_error;
+
+    // Fill up the metadata signature in install plan according to the test.
+    switch (metadata_signature_test) {
+      case kEmptyMetadataSignature:
+        install_plan_.metadata_signature.clear();
+        expected_result = DeltaPerformer::kMetadataParseError;
+        expected_error = ErrorCode::kDownloadMetadataSignatureMissingError;
+        break;
+
+      case kInvalidMetadataSignature:
+        install_plan_.metadata_signature = kBogusMetadataSignature1;
+        expected_result = DeltaPerformer::kMetadataParseError;
+        expected_error = ErrorCode::kDownloadMetadataSignatureMismatch;
+        break;
+
+      case kValidMetadataSignature:
+      default:
+        // Set the install plan's metadata size to be the same as the one
+        // in the manifest so that we pass the metadata size checks. Only
+        // then we can get to manifest signature checks.
+        ASSERT_TRUE(PayloadSigner::GetMetadataSignature(
+            payload.data(),
+            install_plan_.metadata_size,
+            kUnittestPrivateKeyPath,
+            &install_plan_.metadata_signature));
+        EXPECT_FALSE(install_plan_.metadata_signature.empty());
+        expected_result = DeltaPerformer::kMetadataParseSuccess;
+        expected_error = ErrorCode::kSuccess;
+        break;
+    }
+
+    // Ignore the expected result/error if hash checks are not mandatory.
+    if (!hash_checks_mandatory) {
+      expected_result = DeltaPerformer::kMetadataParseSuccess;
+      expected_error = ErrorCode::kSuccess;
+    }
+
+    // Use the public key corresponding to the private key used above to
+    // sign the metadata.
+    EXPECT_TRUE(utils::FileExists(kUnittestPublicKeyPath));
+    performer_.set_public_key_path(kUnittestPublicKeyPath);
+
+    // Init actual_error with an invalid value so that we make sure
+    // ParsePayloadMetadata properly populates it in all cases.
+    actual_error = ErrorCode::kUmaReportedMax;
+    actual_result = performer_.ParsePayloadMetadata(payload, &actual_error);
+
+    EXPECT_EQ(expected_result, actual_result);
+    EXPECT_EQ(expected_error, actual_error);
+
+    // Check that the parsed metadata size is what's expected. This test
+    // implicitly confirms that the metadata signature is valid, if required.
+    EXPECT_EQ(install_plan_.metadata_size, performer_.GetMetadataSize());
+  }
+
+  void SetSupportedMajorVersion(uint64_t major_version) {
+    performer_.supported_major_version_ = major_version;
+  }
+  FakePrefs prefs_;
+  InstallPlan install_plan_;
+  FakeBootControl fake_boot_control_;
+  FakeHardware fake_hardware_;
+  MockDownloadActionDelegate mock_delegate_;
+  DeltaPerformer performer_{
+      &prefs_, &fake_boot_control_, &fake_hardware_, &mock_delegate_, &install_plan_};
+};
+
+TEST_F(DeltaPerformerTest, FullPayloadWriteTest) {
+  install_plan_.is_full_update = true;
+  brillo::Blob expected_data = brillo::Blob(std::begin(kRandomString),
+                                            std::end(kRandomString));
+  expected_data.resize(4096);  // block size
+  vector<AnnotatedOperation> aops;
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(expected_data.size());
+  aop.op.set_type(InstallOperation::REPLACE);
+  aops.push_back(aop);
+
+  brillo::Blob payload_data = GeneratePayload(expected_data, aops, false,
+      kChromeOSMajorPayloadVersion, kFullPayloadMinorVersion);
+
+  EXPECT_EQ(expected_data, ApplyPayload(payload_data, "/dev/null", true));
+}
+
+TEST_F(DeltaPerformerTest, ShouldCancelTest) {
+  install_plan_.is_full_update = true;
+  brillo::Blob expected_data = brillo::Blob(std::begin(kRandomString),
+                                            std::end(kRandomString));
+  expected_data.resize(4096);  // block size
+  vector<AnnotatedOperation> aops;
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(expected_data.size());
+  aop.op.set_type(InstallOperation::REPLACE);
+  aops.push_back(aop);
+
+  brillo::Blob payload_data = GeneratePayload(expected_data, aops, false,
+      kChromeOSMajorPayloadVersion, kFullPayloadMinorVersion);
+
+  testing::Mock::VerifyAndClearExpectations(&mock_delegate_);
+  EXPECT_CALL(mock_delegate_, ShouldCancel(_))
+      .WillOnce(
+          testing::DoAll(testing::SetArgumentPointee<0>(ErrorCode::kError),
+                         testing::Return(true)));
+
+  ApplyPayload(payload_data, "/dev/null", false);
+}
+
+TEST_F(DeltaPerformerTest, ReplaceOperationTest) {
+  brillo::Blob expected_data = brillo::Blob(std::begin(kRandomString),
+                                            std::end(kRandomString));
+  expected_data.resize(4096);  // block size
+  vector<AnnotatedOperation> aops;
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(expected_data.size());
+  aop.op.set_type(InstallOperation::REPLACE);
+  aops.push_back(aop);
+
+  brillo::Blob payload_data = GeneratePayload(expected_data, aops, false);
+
+  EXPECT_EQ(expected_data, ApplyPayload(payload_data, "/dev/null", true));
+}
+
+TEST_F(DeltaPerformerTest, ReplaceBzOperationTest) {
+  brillo::Blob expected_data = brillo::Blob(std::begin(kRandomString),
+                                            std::end(kRandomString));
+  expected_data.resize(4096);  // block size
+  brillo::Blob bz_data;
+  EXPECT_TRUE(BzipCompress(expected_data, &bz_data));
+
+  vector<AnnotatedOperation> aops;
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(bz_data.size());
+  aop.op.set_type(InstallOperation::REPLACE_BZ);
+  aops.push_back(aop);
+
+  brillo::Blob payload_data = GeneratePayload(bz_data, aops, false);
+
+  EXPECT_EQ(expected_data, ApplyPayload(payload_data, "/dev/null", true));
+}
+
+TEST_F(DeltaPerformerTest, ReplaceXzOperationTest) {
+  brillo::Blob xz_data(std::begin(kXzCompressedData),
+                         std::end(kXzCompressedData));
+  // The compressed xz data contains only a single "a", but the operation should
+  // pad the rest of the two blocks with zeros.
+  brillo::Blob expected_data = brillo::Blob(4096, 0);
+  expected_data[0] = 'a';
+
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(xz_data.size());
+  aop.op.set_type(InstallOperation::REPLACE_XZ);
+  vector<AnnotatedOperation> aops = {aop};
+
+  brillo::Blob payload_data = GeneratePayload(xz_data, aops, false);
+
+  EXPECT_EQ(expected_data, ApplyPayload(payload_data, "/dev/null", true));
+}
+
+TEST_F(DeltaPerformerTest, ZeroOperationTest) {
+  brillo::Blob existing_data = brillo::Blob(4096 * 10, 'a');
+  brillo::Blob expected_data = existing_data;
+  // Blocks 4, 5 and 7 should have zeros instead of 'a' after the operation is
+  // applied.
+  std::fill(expected_data.data() + 4096 * 4, expected_data.data() + 4096 * 6,
+            0);
+  std::fill(expected_data.data() + 4096 * 7, expected_data.data() + 4096 * 8,
+            0);
+
+  AnnotatedOperation aop;
+  *(aop.op.add_dst_extents()) = ExtentForRange(4, 2);
+  *(aop.op.add_dst_extents()) = ExtentForRange(7, 1);
+  aop.op.set_type(InstallOperation::ZERO);
+  vector<AnnotatedOperation> aops = {aop};
+
+  brillo::Blob payload_data = GeneratePayload(brillo::Blob(), aops, false);
+
+  EXPECT_EQ(expected_data,
+            ApplyPayloadToData(payload_data, "/dev/null", existing_data, true));
+}
+
+TEST_F(DeltaPerformerTest, SourceCopyOperationTest) {
+  brillo::Blob expected_data(std::begin(kRandomString),
+                             std::end(kRandomString));
+  expected_data.resize(4096);  // block size
+  AnnotatedOperation aop;
+  *(aop.op.add_src_extents()) = ExtentForRange(0, 1);
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_type(InstallOperation::SOURCE_COPY);
+  brillo::Blob src_hash;
+  EXPECT_TRUE(HashCalculator::RawHashOfData(expected_data, &src_hash));
+  aop.op.set_src_sha256_hash(src_hash.data(), src_hash.size());
+
+  brillo::Blob payload_data = GeneratePayload(brillo::Blob(), {aop}, false);
+
+  string source_path;
+  EXPECT_TRUE(utils::MakeTempFile("Source-XXXXXX",
+                                  &source_path, nullptr));
+  ScopedPathUnlinker path_unlinker(source_path);
+  EXPECT_TRUE(utils::WriteFile(source_path.c_str(),
+                               expected_data.data(),
+                               expected_data.size()));
+
+  EXPECT_EQ(expected_data, ApplyPayload(payload_data, source_path, true));
+}
+
+TEST_F(DeltaPerformerTest, SourceHashMismatchTest) {
+  brillo::Blob expected_data = {'f', 'o', 'o'};
+  brillo::Blob actual_data = {'b', 'a', 'r'};
+  expected_data.resize(4096);  // block size
+  actual_data.resize(4096);    // block size
+
+  AnnotatedOperation aop;
+  *(aop.op.add_src_extents()) = ExtentForRange(0, 1);
+  *(aop.op.add_dst_extents()) = ExtentForRange(0, 1);
+  aop.op.set_type(InstallOperation::SOURCE_COPY);
+  brillo::Blob src_hash;
+  EXPECT_TRUE(HashCalculator::RawHashOfData(expected_data, &src_hash));
+  aop.op.set_src_sha256_hash(src_hash.data(), src_hash.size());
+
+  brillo::Blob payload_data = GeneratePayload(brillo::Blob(), {aop}, false);
+
+  string source_path;
+  EXPECT_TRUE(utils::MakeTempFile("Source-XXXXXX", &source_path, nullptr));
+  ScopedPathUnlinker path_unlinker(source_path);
+  EXPECT_TRUE(utils::WriteFile(source_path.c_str(), actual_data.data(),
+                               actual_data.size()));
+
+  EXPECT_EQ(actual_data, ApplyPayload(payload_data, source_path, false));
+}
+
+TEST_F(DeltaPerformerTest, ExtentsToByteStringTest) {
+  uint64_t test[] = {1, 1, 4, 2, 0, 1};
+  COMPILE_ASSERT(arraysize(test) % 2 == 0, array_size_uneven);
+  const uint64_t block_size = 4096;
+  const uint64_t file_length = 4 * block_size - 13;
+
+  google::protobuf::RepeatedPtrField<Extent> extents;
+  for (size_t i = 0; i < arraysize(test); i += 2) {
+    *(extents.Add()) = ExtentForRange(test[i], test[i + 1]);
+  }
+
+  string expected_output = "4096:4096,16384:8192,0:4083";
+  string actual_output;
+  EXPECT_TRUE(DeltaPerformer::ExtentsToBsdiffPositionsString(extents,
+                                                             block_size,
+                                                             file_length,
+                                                             &actual_output));
+  EXPECT_EQ(expected_output, actual_output);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestFullGoodTest) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+  manifest.mutable_new_kernel_info();
+  manifest.mutable_new_rootfs_info();
+  manifest.set_minor_version(kFullPayloadMinorVersion);
+
+  RunManifestValidation(manifest, kChromeOSMajorPayloadVersion, true,
+                        ErrorCode::kSuccess);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestDeltaGoodTest) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+  manifest.mutable_old_kernel_info();
+  manifest.mutable_old_rootfs_info();
+  manifest.mutable_new_kernel_info();
+  manifest.mutable_new_rootfs_info();
+  manifest.set_minor_version(DeltaPerformer::kSupportedMinorPayloadVersion);
+
+  RunManifestValidation(manifest, kChromeOSMajorPayloadVersion, false,
+                        ErrorCode::kSuccess);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestFullUnsetMinorVersion) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+
+  RunManifestValidation(manifest, DeltaPerformer::kSupportedMajorPayloadVersion,
+                        true, ErrorCode::kSuccess);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestDeltaUnsetMinorVersion) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+
+  RunManifestValidation(manifest, DeltaPerformer::kSupportedMajorPayloadVersion,
+                        false, ErrorCode::kUnsupportedMinorPayloadVersion);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestFullOldKernelTest) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+  manifest.mutable_old_kernel_info();
+  manifest.mutable_new_kernel_info();
+  manifest.mutable_new_rootfs_info();
+  manifest.set_minor_version(DeltaPerformer::kSupportedMinorPayloadVersion);
+
+  RunManifestValidation(manifest, kChromeOSMajorPayloadVersion, true,
+                        ErrorCode::kPayloadMismatchedType);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestFullOldRootfsTest) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+  manifest.mutable_old_rootfs_info();
+  manifest.mutable_new_kernel_info();
+  manifest.mutable_new_rootfs_info();
+  manifest.set_minor_version(DeltaPerformer::kSupportedMinorPayloadVersion);
+
+  RunManifestValidation(manifest, kChromeOSMajorPayloadVersion, true,
+                        ErrorCode::kPayloadMismatchedType);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestFullPartitionUpdateTest) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+  PartitionUpdate* partition = manifest.add_partitions();
+  partition->mutable_old_partition_info();
+  partition->mutable_new_partition_info();
+  manifest.set_minor_version(DeltaPerformer::kSupportedMinorPayloadVersion);
+
+  RunManifestValidation(manifest, kBrilloMajorPayloadVersion, true,
+                        ErrorCode::kPayloadMismatchedType);
+}
+
+TEST_F(DeltaPerformerTest, ValidateManifestBadMinorVersion) {
+  // The Manifest we are validating.
+  DeltaArchiveManifest manifest;
+
+  // Generate a bad version number.
+  manifest.set_minor_version(DeltaPerformer::kSupportedMinorPayloadVersion +
+                             10000);
+
+  RunManifestValidation(manifest, DeltaPerformer::kSupportedMajorPayloadVersion,
+                        false, ErrorCode::kUnsupportedMinorPayloadVersion);
+}
+
+TEST_F(DeltaPerformerTest, BrilloMetadataSignatureSizeTest) {
+  EXPECT_TRUE(performer_.Write(kDeltaMagic, sizeof(kDeltaMagic)));
+
+  uint64_t major_version = htobe64(kBrilloMajorPayloadVersion);
+  EXPECT_TRUE(performer_.Write(&major_version, 8));
+
+  uint64_t manifest_size = rand() % 256;
+  uint64_t manifest_size_be = htobe64(manifest_size);
+  EXPECT_TRUE(performer_.Write(&manifest_size_be, 8));
+
+  uint32_t metadata_signature_size = rand() % 256;
+  uint32_t metadata_signature_size_be = htobe32(metadata_signature_size);
+  EXPECT_TRUE(performer_.Write(&metadata_signature_size_be, 4));
+
+  EXPECT_LT(performer_.Close(), 0);
+
+  EXPECT_TRUE(performer_.IsHeaderParsed());
+  EXPECT_EQ(kBrilloMajorPayloadVersion, performer_.GetMajorVersion());
+  uint64_t manifest_offset;
+  EXPECT_TRUE(performer_.GetManifestOffset(&manifest_offset));
+  EXPECT_EQ(24, manifest_offset);  // 4 + 8 + 8 + 4
+  EXPECT_EQ(manifest_offset + manifest_size, performer_.GetMetadataSize());
+  EXPECT_EQ(metadata_signature_size, performer_.metadata_signature_size_);
+}
+
+TEST_F(DeltaPerformerTest, BrilloVerifyMetadataSignatureTest) {
+  brillo::Blob payload_data = GeneratePayload({}, {}, true,
+                                              kBrilloMajorPayloadVersion,
+                                              kSourceMinorPayloadVersion);
+  install_plan_.hash_checks_mandatory = true;
+  // Just set these value so that we can use ValidateMetadataSignature directly.
+  performer_.major_payload_version_ = kBrilloMajorPayloadVersion;
+  performer_.metadata_size_ = install_plan_.metadata_size;
+  uint64_t signature_length;
+  EXPECT_TRUE(PayloadSigner::SignatureBlobLength({kUnittestPrivateKeyPath},
+                                                 &signature_length));
+  performer_.metadata_signature_size_ = signature_length;
+  performer_.set_public_key_path(kUnittestPublicKeyPath);
+  EXPECT_EQ(ErrorCode::kSuccess,
+            performer_.ValidateMetadataSignature(payload_data));
+}
+
+TEST_F(DeltaPerformerTest, BadDeltaMagicTest) {
+  EXPECT_TRUE(performer_.Write("junk", 4));
+  EXPECT_FALSE(performer_.Write("morejunk", 8));
+  EXPECT_LT(performer_.Close(), 0);
+}
+
+TEST_F(DeltaPerformerTest, MissingMandatoryMetadataSizeTest) {
+  DoMetadataSizeTest(0, 75456, true);
+}
+
+TEST_F(DeltaPerformerTest, MissingNonMandatoryMetadataSizeTest) {
+  DoMetadataSizeTest(0, 123456, false);
+}
+
+TEST_F(DeltaPerformerTest, InvalidMandatoryMetadataSizeTest) {
+  DoMetadataSizeTest(13000, 140000, true);
+}
+
+TEST_F(DeltaPerformerTest, InvalidNonMandatoryMetadataSizeTest) {
+  DoMetadataSizeTest(40000, 50000, false);
+}
+
+TEST_F(DeltaPerformerTest, ValidMandatoryMetadataSizeTest) {
+  DoMetadataSizeTest(85376, 85376, true);
+}
+
+TEST_F(DeltaPerformerTest, MandatoryEmptyMetadataSignatureTest) {
+  DoMetadataSignatureTest(kEmptyMetadataSignature, true, true);
+}
+
+TEST_F(DeltaPerformerTest, NonMandatoryEmptyMetadataSignatureTest) {
+  DoMetadataSignatureTest(kEmptyMetadataSignature, true, false);
+}
+
+TEST_F(DeltaPerformerTest, MandatoryInvalidMetadataSignatureTest) {
+  DoMetadataSignatureTest(kInvalidMetadataSignature, true, true);
+}
+
+TEST_F(DeltaPerformerTest, NonMandatoryInvalidMetadataSignatureTest) {
+  DoMetadataSignatureTest(kInvalidMetadataSignature, true, false);
+}
+
+TEST_F(DeltaPerformerTest, MandatoryValidMetadataSignature1Test) {
+  DoMetadataSignatureTest(kValidMetadataSignature, false, true);
+}
+
+TEST_F(DeltaPerformerTest, MandatoryValidMetadataSignature2Test) {
+  DoMetadataSignatureTest(kValidMetadataSignature, true, true);
+}
+
+TEST_F(DeltaPerformerTest, NonMandatoryValidMetadataSignatureTest) {
+  DoMetadataSignatureTest(kValidMetadataSignature, true, false);
+}
+
+TEST_F(DeltaPerformerTest, UsePublicKeyFromResponse) {
+  base::FilePath key_path;
+
+  // The result of the GetPublicKeyResponse() method is based on three things
+  //
+  //  1. Whether it's an official build; and
+  //  2. Whether the Public RSA key to be used is in the root filesystem; and
+  //  3. Whether the response has a public key
+  //
+  // We test all eight combinations to ensure that we only use the
+  // public key in the response if
+  //
+  //  a. it's not an official build; and
+  //  b. there is no key in the root filesystem.
+
+  string temp_dir;
+  EXPECT_TRUE(utils::MakeTempDirectory("PublicKeyFromResponseTests.XXXXXX",
+                                       &temp_dir));
+  string non_existing_file = temp_dir + "/non-existing";
+  string existing_file = temp_dir + "/existing";
+  EXPECT_EQ(0, System(base::StringPrintf("touch %s", existing_file.c_str())));
+
+  // Non-official build, non-existing public-key, key in response -> true
+  fake_hardware_.SetIsOfficialBuild(false);
+  performer_.public_key_path_ = non_existing_file;
+  install_plan_.public_key_rsa = "VGVzdAo="; // result of 'echo "Test" | base64'
+  EXPECT_TRUE(performer_.GetPublicKeyFromResponse(&key_path));
+  EXPECT_FALSE(key_path.empty());
+  EXPECT_EQ(unlink(key_path.value().c_str()), 0);
+  // Same with official build -> false
+  fake_hardware_.SetIsOfficialBuild(true);
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+
+  // Non-official build, existing public-key, key in response -> false
+  fake_hardware_.SetIsOfficialBuild(false);
+  performer_.public_key_path_ = existing_file;
+  install_plan_.public_key_rsa = "VGVzdAo="; // result of 'echo "Test" | base64'
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+  // Same with official build -> false
+  fake_hardware_.SetIsOfficialBuild(true);
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+
+  // Non-official build, non-existing public-key, no key in response -> false
+  fake_hardware_.SetIsOfficialBuild(false);
+  performer_.public_key_path_ = non_existing_file;
+  install_plan_.public_key_rsa = "";
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+  // Same with official build -> false
+  fake_hardware_.SetIsOfficialBuild(true);
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+
+  // Non-official build, existing public-key, no key in response -> false
+  fake_hardware_.SetIsOfficialBuild(false);
+  performer_.public_key_path_ = existing_file;
+  install_plan_.public_key_rsa = "";
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+  // Same with official build -> false
+  fake_hardware_.SetIsOfficialBuild(true);
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+
+  // Non-official build, non-existing public-key, key in response
+  // but invalid base64 -> false
+  fake_hardware_.SetIsOfficialBuild(false);
+  performer_.public_key_path_ = non_existing_file;
+  install_plan_.public_key_rsa = "not-valid-base64";
+  EXPECT_FALSE(performer_.GetPublicKeyFromResponse(&key_path));
+
+  EXPECT_TRUE(base::DeleteFile(base::FilePath(temp_dir), true));
+}
+
+TEST_F(DeltaPerformerTest, ConfVersionsMatch) {
+  // Test that the versions in update_engine.conf that is installed to the
+  // image match the supported delta versions in the update engine.
+  uint32_t minor_version;
+  brillo::KeyValueStore store;
+  EXPECT_TRUE(store.Load(base::FilePath("update_engine.conf")));
+  EXPECT_TRUE(utils::GetMinorVersion(store, &minor_version));
+  EXPECT_EQ(DeltaPerformer::kSupportedMinorPayloadVersion, minor_version);
+
+  string major_version_str;
+  uint64_t major_version;
+  EXPECT_TRUE(store.GetString("PAYLOAD_MAJOR_VERSION", &major_version_str));
+  EXPECT_TRUE(base::StringToUint64(major_version_str, &major_version));
+  EXPECT_EQ(DeltaPerformer::kSupportedMajorPayloadVersion, major_version);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/download_action.cc b/payload_consumer/download_action.cc
new file mode 100644
index 0000000..cb404b8
--- /dev/null
+++ b/payload_consumer/download_action.cc
@@ -0,0 +1,318 @@
+//
+// Copyright (C) 2011 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 "update_engine/payload_consumer/download_action.h"
+
+#include <errno.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/action_pipe.h"
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/p2p_manager.h"
+#include "update_engine/payload_state_interface.h"
+
+using base::FilePath;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+DownloadAction::DownloadAction(PrefsInterface* prefs,
+                               SystemState* system_state,
+                               HttpFetcher* http_fetcher)
+    : prefs_(prefs),
+      system_state_(system_state),
+      http_fetcher_(http_fetcher),
+      writer_(nullptr),
+      code_(ErrorCode::kSuccess),
+      delegate_(nullptr),
+      bytes_received_(0),
+      p2p_sharing_fd_(-1),
+      p2p_visible_(true) {}
+
+DownloadAction::~DownloadAction() {}
+
+void DownloadAction::CloseP2PSharingFd(bool delete_p2p_file) {
+  if (p2p_sharing_fd_ != -1) {
+    if (close(p2p_sharing_fd_) != 0) {
+      PLOG(ERROR) << "Error closing p2p sharing fd";
+    }
+    p2p_sharing_fd_ = -1;
+  }
+
+  if (delete_p2p_file) {
+    FilePath path =
+      system_state_->p2p_manager()->FileGetPath(p2p_file_id_);
+    if (unlink(path.value().c_str()) != 0) {
+      PLOG(ERROR) << "Error deleting p2p file " << path.value();
+    } else {
+      LOG(INFO) << "Deleted p2p file " << path.value();
+    }
+  }
+
+  // Don't use p2p from this point onwards.
+  p2p_file_id_.clear();
+}
+
+bool DownloadAction::SetupP2PSharingFd() {
+  P2PManager *p2p_manager = system_state_->p2p_manager();
+
+  if (!p2p_manager->FileShare(p2p_file_id_, install_plan_.payload_size)) {
+    LOG(ERROR) << "Unable to share file via p2p";
+    CloseP2PSharingFd(true);  // delete p2p file
+    return false;
+  }
+
+  // File has already been created (and allocated, xattrs been
+  // populated etc.) by FileShare() so just open it for writing.
+  FilePath path = p2p_manager->FileGetPath(p2p_file_id_);
+  p2p_sharing_fd_ = open(path.value().c_str(), O_WRONLY);
+  if (p2p_sharing_fd_ == -1) {
+    PLOG(ERROR) << "Error opening file " << path.value();
+    CloseP2PSharingFd(true);  // Delete p2p file.
+    return false;
+  }
+
+  // Ensure file to share is world-readable, otherwise
+  // p2p-server and p2p-http-server can't access it.
+  //
+  // (Q: Why doesn't the file have mode 0644 already? A: Because
+  // the process-wide umask is set to 0700 in main.cc.)
+  if (fchmod(p2p_sharing_fd_, 0644) != 0) {
+    PLOG(ERROR) << "Error setting mode 0644 on " << path.value();
+    CloseP2PSharingFd(true);  // Delete p2p file.
+    return false;
+  }
+
+  // All good.
+  LOG(INFO) << "Writing payload contents to " << path.value();
+  p2p_manager->FileGetVisible(p2p_file_id_, &p2p_visible_);
+  return true;
+}
+
+void DownloadAction::WriteToP2PFile(const void* data,
+                                    size_t length,
+                                    off_t file_offset) {
+  if (p2p_sharing_fd_ == -1) {
+    if (!SetupP2PSharingFd())
+      return;
+  }
+
+  // Check that the file is at least |file_offset| bytes long - if
+  // it's not something is wrong and we must immediately delete the
+  // file to avoid propagating this problem to other peers.
+  //
+  // How can this happen? It could be that we're resuming an update
+  // after a system crash... in this case, it could be that
+  //
+  //  1. the p2p file didn't get properly synced to stable storage; or
+  //  2. the file was deleted at bootup (it's in /var/cache after all); or
+  //  3. other reasons
+  off_t p2p_size = utils::FileSize(p2p_sharing_fd_);
+  if (p2p_size < 0) {
+    PLOG(ERROR) << "Error getting file status for p2p file";
+    CloseP2PSharingFd(true);  // Delete p2p file.
+    return;
+  }
+  if (p2p_size < file_offset) {
+    LOG(ERROR) << "Wanting to write to file offset " << file_offset
+               << " but existing p2p file is only " << p2p_size
+               << " bytes.";
+    CloseP2PSharingFd(true);  // Delete p2p file.
+    return;
+  }
+
+  off_t cur_file_offset = lseek(p2p_sharing_fd_, file_offset, SEEK_SET);
+  if (cur_file_offset != static_cast<off_t>(file_offset)) {
+    PLOG(ERROR) << "Error seeking to position "
+                << file_offset << " in p2p file";
+    CloseP2PSharingFd(true);  // Delete p2p file.
+  } else {
+    // OK, seeking worked, now write the data
+    ssize_t bytes_written = write(p2p_sharing_fd_, data, length);
+    if (bytes_written != static_cast<ssize_t>(length)) {
+      PLOG(ERROR) << "Error writing "
+                  << length << " bytes at file offset "
+                  << file_offset << " in p2p file";
+      CloseP2PSharingFd(true);  // Delete p2p file.
+    }
+  }
+}
+
+void DownloadAction::PerformAction() {
+  http_fetcher_->set_delegate(this);
+
+  // Get the InstallPlan and read it
+  CHECK(HasInputObject());
+  install_plan_ = GetInputObject();
+  bytes_received_ = 0;
+
+  install_plan_.Dump();
+
+  LOG(INFO) << "Marking new slot as unbootable";
+  if (!system_state_->boot_control()->MarkSlotUnbootable(
+          install_plan_.target_slot)) {
+    LOG(WARNING) << "Unable to mark new slot "
+                 << BootControlInterface::SlotName(install_plan_.target_slot)
+                 << ". Proceeding with the update anyway.";
+  }
+
+  if (writer_) {
+    LOG(INFO) << "Using writer for test.";
+  } else {
+    delta_performer_.reset(new DeltaPerformer(prefs_,
+                                              system_state_->boot_control(),
+                                              system_state_->hardware(),
+                                              delegate_,
+                                              &install_plan_));
+    writer_ = delta_performer_.get();
+  }
+  download_active_= true;
+
+  if (system_state_ != nullptr) {
+    const PayloadStateInterface* payload_state = system_state_->payload_state();
+    string file_id = utils::CalculateP2PFileId(install_plan_.payload_hash,
+                                               install_plan_.payload_size);
+    if (payload_state->GetUsingP2PForSharing()) {
+      // If we're sharing the update, store the file_id to convey
+      // that we should write to the file.
+      p2p_file_id_ = file_id;
+      LOG(INFO) << "p2p file id: " << p2p_file_id_;
+    } else {
+      // Even if we're not sharing the update, it could be that
+      // there's a partial file from a previous attempt with the same
+      // hash. If this is the case, we NEED to clean it up otherwise
+      // we're essentially timing out other peers downloading from us
+      // (since we're never going to complete the file).
+      FilePath path = system_state_->p2p_manager()->FileGetPath(file_id);
+      if (!path.empty()) {
+        if (unlink(path.value().c_str()) != 0) {
+          PLOG(ERROR) << "Error deleting p2p file " << path.value();
+        } else {
+          LOG(INFO) << "Deleting partial p2p file " << path.value()
+                    << " since we're not using p2p to share.";
+        }
+      }
+    }
+
+    // Tweak timeouts on the HTTP fetcher if we're downloading from a
+    // local peer.
+    if (payload_state->GetUsingP2PForDownloading() &&
+        payload_state->GetP2PUrl() == install_plan_.download_url) {
+      LOG(INFO) << "Tweaking HTTP fetcher since we're downloading via p2p";
+      http_fetcher_->set_low_speed_limit(kDownloadP2PLowSpeedLimitBps,
+                                         kDownloadP2PLowSpeedTimeSeconds);
+      http_fetcher_->set_max_retry_count(kDownloadP2PMaxRetryCount);
+      http_fetcher_->set_connect_timeout(kDownloadP2PConnectTimeoutSeconds);
+    }
+  }
+
+  http_fetcher_->BeginTransfer(install_plan_.download_url);
+}
+
+void DownloadAction::TerminateProcessing() {
+  if (writer_) {
+    writer_->Close();
+    writer_ = nullptr;
+  }
+  download_active_= false;
+  CloseP2PSharingFd(false);  // Keep p2p file.
+  // Terminates the transfer. The action is terminated, if necessary, when the
+  // TransferTerminated callback is received.
+  http_fetcher_->TerminateTransfer();
+}
+
+void DownloadAction::SeekToOffset(off_t offset) {
+  bytes_received_ = offset;
+}
+
+void DownloadAction::ReceivedBytes(HttpFetcher* fetcher,
+                                   const void* bytes,
+                                   size_t length) {
+  // Note that bytes_received_ is the current offset.
+  if (!p2p_file_id_.empty()) {
+    WriteToP2PFile(bytes, length, bytes_received_);
+  }
+
+  bytes_received_ += length;
+  if (delegate_ && download_active_) {
+    delegate_->BytesReceived(
+        length, bytes_received_, install_plan_.payload_size);
+  }
+  if (writer_ && !writer_->Write(bytes, length, &code_)) {
+    LOG(ERROR) << "Error " << code_ << " in DeltaPerformer's Write method when "
+               << "processing the received payload -- Terminating processing";
+    // Delete p2p file, if applicable.
+    if (!p2p_file_id_.empty())
+      CloseP2PSharingFd(true);
+    // Don't tell the action processor that the action is complete until we get
+    // the TransferTerminated callback. Otherwise, this and the HTTP fetcher
+    // objects may get destroyed before all callbacks are complete.
+    TerminateProcessing();
+    return;
+  }
+
+  // Call p2p_manager_->FileMakeVisible() when we've successfully
+  // verified the manifest!
+  if (!p2p_visible_ &&
+      delta_performer_.get() && delta_performer_->IsManifestValid()) {
+    LOG(INFO) << "Manifest has been validated. Making p2p file visible.";
+    system_state_->p2p_manager()->FileMakeVisible(p2p_file_id_);
+    p2p_visible_ = true;
+  }
+}
+
+void DownloadAction::TransferComplete(HttpFetcher* fetcher, bool successful) {
+  if (writer_) {
+    LOG_IF(WARNING, writer_->Close() != 0) << "Error closing the writer.";
+    writer_ = nullptr;
+  }
+  download_active_= false;
+  ErrorCode code =
+      successful ? ErrorCode::kSuccess : ErrorCode::kDownloadTransferError;
+  if (code == ErrorCode::kSuccess && delta_performer_.get()) {
+    code = delta_performer_->VerifyPayload(install_plan_.payload_hash,
+                                           install_plan_.payload_size);
+    if (code != ErrorCode::kSuccess) {
+      LOG(ERROR) << "Download of " << install_plan_.download_url
+                 << " failed due to payload verification error.";
+      // Delete p2p file, if applicable.
+      if (!p2p_file_id_.empty())
+        CloseP2PSharingFd(true);
+    }
+  }
+
+  // Write the path to the output pipe if we're successful.
+  if (code == ErrorCode::kSuccess && HasOutputPipe())
+    SetOutputObject(install_plan_);
+  processor_->ActionComplete(this, code);
+}
+
+void DownloadAction::TransferTerminated(HttpFetcher *fetcher) {
+  if (code_ != ErrorCode::kSuccess) {
+    processor_->ActionComplete(this, code_);
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/download_action.h b/payload_consumer/download_action.h
new file mode 100644
index 0000000..300d97e
--- /dev/null
+++ b/payload_consumer/download_action.h
@@ -0,0 +1,175 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_DOWNLOAD_ACTION_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_DOWNLOAD_ACTION_H_
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <memory>
+#include <string>
+
+#include <curl/curl.h>
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/http_fetcher.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/install_plan.h"
+#include "update_engine/system_state.h"
+
+// The Download Action downloads a specified url to disk. The url should point
+// to an update in a delta payload format. The payload will be piped into a
+// DeltaPerformer that will apply the delta to the disk.
+
+namespace chromeos_update_engine {
+
+class DownloadActionDelegate {
+ public:
+  virtual ~DownloadActionDelegate() = default;
+
+  // Called periodically after bytes are received. This method will be invoked
+  // only if the DownloadAction is running. |bytes_progressed| is the number of
+  // bytes downloaded since the last call of this method, |bytes_received|
+  // the number of bytes downloaded thus far and |total| is the number of bytes
+  // expected.
+  virtual void BytesReceived(uint64_t bytes_progressed,
+                             uint64_t bytes_received,
+                             uint64_t total) = 0;
+
+  // Returns whether the download should be canceled, in which case the
+  // |cancel_reason| error should be set to the reason why the download was
+  // canceled.
+  virtual bool ShouldCancel(ErrorCode* cancel_reason) = 0;
+
+  // Called once the complete payload has been downloaded. Note that any errors
+  // while applying or downloading the partial payload will result in this
+  // method not being called.
+  virtual void DownloadComplete() = 0;
+};
+
+class PrefsInterface;
+
+class DownloadAction : public InstallPlanAction,
+                       public HttpFetcherDelegate {
+ public:
+  // Takes ownership of the passed in HttpFetcher. Useful for testing.
+  // A good calling pattern is:
+  // DownloadAction(prefs, system_state, new WhateverHttpFetcher);
+  DownloadAction(PrefsInterface* prefs,
+                 SystemState* system_state,
+                 HttpFetcher* http_fetcher);
+  ~DownloadAction() override;
+  void PerformAction() override;
+  void TerminateProcessing() override;
+
+  // Testing
+  void SetTestFileWriter(FileWriter* writer) {
+    writer_ = writer;
+  }
+
+  int GetHTTPResponseCode() { return http_fetcher_->http_response_code(); }
+
+  // Debugging/logging
+  static std::string StaticType() { return "DownloadAction"; }
+  std::string Type() const override { return StaticType(); }
+
+  // HttpFetcherDelegate methods (see http_fetcher.h)
+  void ReceivedBytes(HttpFetcher* fetcher,
+                     const void* bytes, size_t length) override;
+  void SeekToOffset(off_t offset) override;
+  void TransferComplete(HttpFetcher* fetcher, bool successful) override;
+  void TransferTerminated(HttpFetcher* fetcher) override;
+
+  DownloadActionDelegate* delegate() const { return delegate_; }
+  void set_delegate(DownloadActionDelegate* delegate) {
+    delegate_ = delegate;
+  }
+
+  HttpFetcher* http_fetcher() { return http_fetcher_.get(); }
+
+  // Returns the p2p file id for the file being written or the empty
+  // string if we're not writing to a p2p file.
+  std::string p2p_file_id() { return p2p_file_id_; }
+
+ private:
+  // Closes the file descriptor for the p2p file being written and
+  // clears |p2p_file_id_| to indicate that we're no longer sharing
+  // the file. If |delete_p2p_file| is True, also deletes the file.
+  // If there is no p2p file descriptor, this method does nothing.
+  void CloseP2PSharingFd(bool delete_p2p_file);
+
+  // Starts sharing the p2p file. Must be called before
+  // WriteToP2PFile(). Returns True if this worked.
+  bool SetupP2PSharingFd();
+
+  // Writes |length| bytes of payload from |data| into |file_offset|
+  // of the p2p file. Also does sanity checks; for example ensures we
+  // don't end up with a file with holes in it.
+  //
+  // This method does nothing if SetupP2PSharingFd() hasn't been
+  // called or if CloseP2PSharingFd() has been called.
+  void WriteToP2PFile(const void* data, size_t length, off_t file_offset);
+
+  // The InstallPlan passed in
+  InstallPlan install_plan_;
+
+  // Update Engine preference store.
+  PrefsInterface* prefs_;
+
+  // Global context for the system.
+  SystemState* system_state_;
+
+  // Pointer to the HttpFetcher that does the http work.
+  std::unique_ptr<HttpFetcher> http_fetcher_;
+
+  // The FileWriter that downloaded data should be written to. It will
+  // either point to *decompressing_file_writer_ or *delta_performer_.
+  FileWriter* writer_;
+
+  std::unique_ptr<DeltaPerformer> delta_performer_;
+
+  // Used by TransferTerminated to figure if this action terminated itself or
+  // was terminated by the action processor.
+  ErrorCode code_;
+
+  // For reporting status to outsiders
+  DownloadActionDelegate* delegate_;
+  uint64_t bytes_received_;
+  bool download_active_{false};
+
+  // The file-id for the file we're sharing or the empty string
+  // if we're not using p2p to share.
+  std::string p2p_file_id_;
+
+  // The file descriptor for the p2p file used for caching the payload or -1
+  // if we're not using p2p to share.
+  int p2p_sharing_fd_;
+
+  // Set to |false| if p2p file is not visible.
+  bool p2p_visible_;
+
+  DISALLOW_COPY_AND_ASSIGN(DownloadAction);
+};
+
+// We want to be sure that we're compiled with large file support on linux,
+// just in case we find ourselves downloading large images.
+COMPILE_ASSERT(8 == sizeof(off_t), off_t_not_64_bit);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_DOWNLOAD_ACTION_H_
diff --git a/payload_consumer/download_action_unittest.cc b/payload_consumer/download_action_unittest.cc
new file mode 100644
index 0000000..08053bf
--- /dev/null
+++ b/payload_consumer/download_action_unittest.cc
@@ -0,0 +1,626 @@
+//
+// Copyright (C) 2011 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 "update_engine/payload_consumer/download_action.h"
+
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/location.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/action_pipe.h"
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/mock_http_fetcher.h"
+#include "update_engine/common/mock_prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_p2p_manager_configuration.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/payload_consumer/mock_download_action.h"
+#include "update_engine/update_manager/fake_update_manager.h"
+
+namespace chromeos_update_engine {
+
+using base::FilePath;
+using base::ReadFileToString;
+using base::WriteFile;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+using test_utils::ScopedTempFile;
+using testing::AtLeast;
+using testing::InSequence;
+using testing::Return;
+using testing::_;
+
+class DownloadActionTest : public ::testing::Test { };
+
+namespace {
+
+class DownloadActionTestProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  explicit DownloadActionTestProcessorDelegate(ErrorCode expected_code)
+      : processing_done_called_(false),
+        expected_code_(expected_code) {}
+  ~DownloadActionTestProcessorDelegate() override {
+    EXPECT_TRUE(processing_done_called_);
+  }
+  void ProcessingDone(const ActionProcessor* processor,
+                      ErrorCode code) override {
+    brillo::MessageLoop::current()->BreakLoop();
+    brillo::Blob found_data;
+    ASSERT_TRUE(utils::ReadFile(path_, &found_data));
+    if (expected_code_ != ErrorCode::kDownloadWriteError) {
+      ASSERT_EQ(expected_data_.size(), found_data.size());
+      for (unsigned i = 0; i < expected_data_.size(); i++) {
+        EXPECT_EQ(expected_data_[i], found_data[i]);
+      }
+    }
+    processing_done_called_ = true;
+  }
+
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) override {
+    const string type = action->Type();
+    if (type == DownloadAction::StaticType()) {
+      EXPECT_EQ(expected_code_, code);
+    } else {
+      EXPECT_EQ(ErrorCode::kSuccess, code);
+    }
+  }
+
+  string path_;
+  brillo::Blob expected_data_;
+  bool processing_done_called_;
+  ErrorCode expected_code_;
+};
+
+class TestDirectFileWriter : public DirectFileWriter {
+ public:
+  TestDirectFileWriter() : fail_write_(0), current_write_(0) {}
+  void set_fail_write(int fail_write) { fail_write_ = fail_write; }
+
+  virtual bool Write(const void* bytes, size_t count) {
+    if (++current_write_ == fail_write_) {
+      return false;
+    }
+    return DirectFileWriter::Write(bytes, count);
+  }
+
+ private:
+  // If positive, fail on the |fail_write_| call to Write.
+  int fail_write_;
+  int current_write_;
+};
+
+void StartProcessorInRunLoop(ActionProcessor* processor,
+                             MockHttpFetcher* http_fetcher) {
+  processor->StartProcessing();
+  http_fetcher->SetOffset(1);
+}
+
+void TestWithData(const brillo::Blob& data,
+                  int fail_write,
+                  bool use_download_delegate) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+  FakeSystemState fake_system_state;
+
+  // TODO(adlr): see if we need a different file for build bots
+  ScopedTempFile output_temp_file;
+  TestDirectFileWriter writer;
+  EXPECT_EQ(0, writer.Open(output_temp_file.GetPath().c_str(),
+                           O_WRONLY | O_CREAT,
+                           0));
+  writer.set_fail_write(fail_write);
+
+  // We pull off the first byte from data and seek past it.
+  string hash = HashCalculator::HashOfBytes(&data[1], data.size() - 1);
+  uint64_t size = data.size();
+  InstallPlan install_plan(false,
+                           false,
+                           "",
+                           size,
+                           hash,
+                           0,
+                           "",
+                           "");
+  install_plan.source_slot = 0;
+  install_plan.target_slot = 1;
+  // We mark both slots as bootable. Only the target slot should be unbootable
+  // after the download starts.
+  fake_system_state.fake_boot_control()->SetSlotBootable(
+      install_plan.source_slot, true);
+  fake_system_state.fake_boot_control()->SetSlotBootable(
+      install_plan.target_slot, true);
+  ObjectFeederAction<InstallPlan> feeder_action;
+  feeder_action.set_obj(install_plan);
+  MockPrefs prefs;
+  MockHttpFetcher* http_fetcher = new MockHttpFetcher(data.data(),
+                                                      data.size(),
+                                                      nullptr);
+  // takes ownership of passed in HttpFetcher
+  DownloadAction download_action(&prefs, &fake_system_state, http_fetcher);
+  download_action.SetTestFileWriter(&writer);
+  BondActions(&feeder_action, &download_action);
+  MockDownloadActionDelegate download_delegate;
+  if (use_download_delegate) {
+    InSequence s;
+    download_action.set_delegate(&download_delegate);
+    if (data.size() > kMockHttpFetcherChunkSize)
+      EXPECT_CALL(download_delegate,
+                  BytesReceived(_, 1 + kMockHttpFetcherChunkSize, _));
+    EXPECT_CALL(download_delegate, BytesReceived(_, _, _)).Times(AtLeast(1));
+  }
+  ErrorCode expected_code = ErrorCode::kSuccess;
+  if (fail_write > 0)
+    expected_code = ErrorCode::kDownloadWriteError;
+  DownloadActionTestProcessorDelegate delegate(expected_code);
+  delegate.expected_data_ = brillo::Blob(data.begin() + 1, data.end());
+  delegate.path_ = output_temp_file.GetPath();
+  ActionProcessor processor;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&download_action);
+
+  loop.PostTask(FROM_HERE,
+                base::Bind(&StartProcessorInRunLoop, &processor, http_fetcher));
+  loop.Run();
+  EXPECT_FALSE(loop.PendingTasks());
+
+  EXPECT_TRUE(fake_system_state.fake_boot_control()->IsSlotBootable(
+      install_plan.source_slot));
+  EXPECT_FALSE(fake_system_state.fake_boot_control()->IsSlotBootable(
+      install_plan.target_slot));
+}
+}  // namespace
+
+TEST(DownloadActionTest, SimpleTest) {
+  brillo::Blob small;
+  const char* foo = "foo";
+  small.insert(small.end(), foo, foo + strlen(foo));
+  TestWithData(small,
+               0,  // fail_write
+               true);  // use_download_delegate
+}
+
+TEST(DownloadActionTest, LargeTest) {
+  brillo::Blob big(5 * kMockHttpFetcherChunkSize);
+  char c = '0';
+  for (unsigned int i = 0; i < big.size(); i++) {
+    big[i] = c;
+    c = ('9' == c) ? '0' : c + 1;
+  }
+  TestWithData(big,
+               0,  // fail_write
+               true);  // use_download_delegate
+}
+
+TEST(DownloadActionTest, FailWriteTest) {
+  brillo::Blob big(5 * kMockHttpFetcherChunkSize);
+  char c = '0';
+  for (unsigned int i = 0; i < big.size(); i++) {
+    big[i] = c;
+    c = ('9' == c) ? '0' : c + 1;
+  }
+  TestWithData(big,
+               2,  // fail_write
+               true);  // use_download_delegate
+}
+
+TEST(DownloadActionTest, NoDownloadDelegateTest) {
+  brillo::Blob small;
+  const char* foo = "foofoo";
+  small.insert(small.end(), foo, foo + strlen(foo));
+  TestWithData(small,
+               0,  // fail_write
+               false);  // use_download_delegate
+}
+
+namespace {
+class TerminateEarlyTestProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  void ProcessingStopped(const ActionProcessor* processor) {
+    brillo::MessageLoop::current()->BreakLoop();
+  }
+};
+
+void TerminateEarlyTestStarter(ActionProcessor* processor) {
+  processor->StartProcessing();
+  CHECK(processor->IsRunning());
+  processor->StopProcessing();
+}
+
+void TestTerminateEarly(bool use_download_delegate) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+
+  brillo::Blob data(kMockHttpFetcherChunkSize +
+                      kMockHttpFetcherChunkSize / 2);
+  memset(data.data(), 0, data.size());
+
+  ScopedTempFile temp_file;
+  {
+    DirectFileWriter writer;
+    EXPECT_EQ(0, writer.Open(temp_file.GetPath().c_str(),
+                             O_WRONLY | O_CREAT,
+                             0));
+
+    // takes ownership of passed in HttpFetcher
+    ObjectFeederAction<InstallPlan> feeder_action;
+    InstallPlan install_plan(false, false, "", 0, "", 0, "", "");
+    feeder_action.set_obj(install_plan);
+    FakeSystemState fake_system_state_;
+    MockPrefs prefs;
+    DownloadAction download_action(&prefs, &fake_system_state_,
+                                   new MockHttpFetcher(data.data(),
+                                                       data.size(),
+                                                       nullptr));
+    download_action.SetTestFileWriter(&writer);
+    MockDownloadActionDelegate download_delegate;
+    if (use_download_delegate) {
+      download_action.set_delegate(&download_delegate);
+      EXPECT_CALL(download_delegate, BytesReceived(_, _, _)).Times(0);
+    }
+    TerminateEarlyTestProcessorDelegate delegate;
+    ActionProcessor processor;
+    processor.set_delegate(&delegate);
+    processor.EnqueueAction(&feeder_action);
+    processor.EnqueueAction(&download_action);
+    BondActions(&feeder_action, &download_action);
+
+    loop.PostTask(FROM_HERE,
+                  base::Bind(&TerminateEarlyTestStarter, &processor));
+    loop.Run();
+    EXPECT_FALSE(loop.PendingTasks());
+  }
+
+  // 1 or 0 chunks should have come through
+  const off_t resulting_file_size(utils::FileSize(temp_file.GetPath()));
+  EXPECT_GE(resulting_file_size, 0);
+  if (resulting_file_size != 0)
+    EXPECT_EQ(kMockHttpFetcherChunkSize, resulting_file_size);
+}
+
+}  // namespace
+
+TEST(DownloadActionTest, TerminateEarlyTest) {
+  TestTerminateEarly(true);
+}
+
+TEST(DownloadActionTest, TerminateEarlyNoDownloadDelegateTest) {
+  TestTerminateEarly(false);
+}
+
+class DownloadActionTestAction;
+
+template<>
+class ActionTraits<DownloadActionTestAction> {
+ public:
+  typedef InstallPlan OutputObjectType;
+  typedef InstallPlan InputObjectType;
+};
+
+// This is a simple Action class for testing.
+class DownloadActionTestAction : public Action<DownloadActionTestAction> {
+ public:
+  DownloadActionTestAction() : did_run_(false) {}
+  typedef InstallPlan InputObjectType;
+  typedef InstallPlan OutputObjectType;
+  ActionPipe<InstallPlan>* in_pipe() { return in_pipe_.get(); }
+  ActionPipe<InstallPlan>* out_pipe() { return out_pipe_.get(); }
+  ActionProcessor* processor() { return processor_; }
+  void PerformAction() {
+    did_run_ = true;
+    ASSERT_TRUE(HasInputObject());
+    EXPECT_TRUE(expected_input_object_ == GetInputObject());
+    ASSERT_TRUE(processor());
+    processor()->ActionComplete(this, ErrorCode::kSuccess);
+  }
+  string Type() const { return "DownloadActionTestAction"; }
+  InstallPlan expected_input_object_;
+  bool did_run_;
+};
+
+namespace {
+// This class is an ActionProcessorDelegate that simply terminates the
+// run loop when the ActionProcessor has completed processing. It's used
+// only by the test PassObjectOutTest.
+class PassObjectOutTestProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  void ProcessingDone(const ActionProcessor* processor, ErrorCode code) {
+    brillo::MessageLoop::current()->BreakLoop();
+  }
+};
+
+}  // namespace
+
+TEST(DownloadActionTest, PassObjectOutTest) {
+  brillo::FakeMessageLoop loop(nullptr);
+  loop.SetAsCurrent();
+
+  DirectFileWriter writer;
+  EXPECT_EQ(0, writer.Open("/dev/null", O_WRONLY | O_CREAT, 0));
+
+  // takes ownership of passed in HttpFetcher
+  InstallPlan install_plan(false,
+                           false,
+                           "",
+                           1,
+                           HashCalculator::HashOfString("x"),
+                           0,
+                           "",
+                           "");
+  ObjectFeederAction<InstallPlan> feeder_action;
+  feeder_action.set_obj(install_plan);
+  MockPrefs prefs;
+  FakeSystemState fake_system_state_;
+  DownloadAction download_action(&prefs, &fake_system_state_,
+                                 new MockHttpFetcher("x", 1, nullptr));
+  download_action.SetTestFileWriter(&writer);
+
+  DownloadActionTestAction test_action;
+  test_action.expected_input_object_ = install_plan;
+  BondActions(&feeder_action, &download_action);
+  BondActions(&download_action, &test_action);
+
+  ActionProcessor processor;
+  PassObjectOutTestProcessorDelegate delegate;
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&download_action);
+  processor.EnqueueAction(&test_action);
+
+  loop.PostTask(FROM_HERE,
+                base::Bind([&processor] { processor.StartProcessing(); }));
+  loop.Run();
+  EXPECT_FALSE(loop.PendingTasks());
+
+  EXPECT_EQ(true, test_action.did_run_);
+}
+
+// Test fixture for P2P tests.
+class P2PDownloadActionTest : public testing::Test {
+ protected:
+  P2PDownloadActionTest()
+    : start_at_offset_(0),
+      fake_um_(fake_system_state_.fake_clock()) {}
+
+  ~P2PDownloadActionTest() override {}
+
+  // Derived from testing::Test.
+  void SetUp() override {
+    loop_.SetAsCurrent();
+  }
+
+  // Derived from testing::Test.
+  void TearDown() override {
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  // To be called by tests to setup the download. The
+  // |starting_offset| parameter is for where to resume.
+  void SetupDownload(off_t starting_offset) {
+    start_at_offset_ = starting_offset;
+    // Prepare data 10 kB of data.
+    data_.clear();
+    for (unsigned int i = 0; i < 10 * 1000; i++)
+      data_ += 'a' + (i % 25);
+
+    // Setup p2p.
+    FakeP2PManagerConfiguration *test_conf = new FakeP2PManagerConfiguration();
+    p2p_manager_.reset(P2PManager::Construct(
+        test_conf, nullptr, &fake_um_, "cros_au", 3,
+        base::TimeDelta::FromDays(5)));
+    fake_system_state_.set_p2p_manager(p2p_manager_.get());
+  }
+
+  // To be called by tests to perform the download. The
+  // |use_p2p_to_share| parameter is used to indicate whether the
+  // payload should be shared via p2p.
+  void StartDownload(bool use_p2p_to_share) {
+    EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+                GetUsingP2PForSharing())
+        .WillRepeatedly(Return(use_p2p_to_share));
+
+    ScopedTempFile output_temp_file;
+    TestDirectFileWriter writer;
+    EXPECT_EQ(0, writer.Open(output_temp_file.GetPath().c_str(),
+                             O_WRONLY | O_CREAT,
+                             0));
+    InstallPlan install_plan(false,
+                             false,
+                             "",
+                             data_.length(),
+                             "1234hash",
+                             0,
+                             "",
+                             "");
+    ObjectFeederAction<InstallPlan> feeder_action;
+    feeder_action.set_obj(install_plan);
+    MockPrefs prefs;
+    http_fetcher_ = new MockHttpFetcher(data_.c_str(),
+                                        data_.length(),
+                                        nullptr);
+    // Note that DownloadAction takes ownership of the passed in HttpFetcher.
+    download_action_.reset(new DownloadAction(&prefs, &fake_system_state_,
+                                              http_fetcher_));
+    download_action_->SetTestFileWriter(&writer);
+    BondActions(&feeder_action, download_action_.get());
+    DownloadActionTestProcessorDelegate delegate(ErrorCode::kSuccess);
+    delegate.expected_data_ = brillo::Blob(data_.begin() + start_at_offset_,
+                                           data_.end());
+    delegate.path_ = output_temp_file.GetPath();
+    processor_.set_delegate(&delegate);
+    processor_.EnqueueAction(&feeder_action);
+    processor_.EnqueueAction(download_action_.get());
+
+    loop_.PostTask(FROM_HERE, base::Bind(
+        &P2PDownloadActionTest::StartProcessorInRunLoopForP2P,
+        base::Unretained(this)));
+    loop_.Run();
+  }
+
+  // Mainloop used to make StartDownload() synchronous.
+  brillo::FakeMessageLoop loop_{nullptr};
+
+  // The DownloadAction instance under test.
+  unique_ptr<DownloadAction> download_action_;
+
+  // The HttpFetcher used in the test.
+  MockHttpFetcher* http_fetcher_;
+
+  // The P2PManager used in the test.
+  unique_ptr<P2PManager> p2p_manager_;
+
+  // The ActionProcessor used for running the actions.
+  ActionProcessor processor_;
+
+  // A fake system state.
+  FakeSystemState fake_system_state_;
+
+  // The data being downloaded.
+  string data_;
+
+ private:
+  // Callback used in StartDownload() method.
+  void StartProcessorInRunLoopForP2P() {
+    processor_.StartProcessing();
+    http_fetcher_->SetOffset(start_at_offset_);
+  }
+
+  // The requested starting offset passed to SetupDownload().
+  off_t start_at_offset_;
+
+  chromeos_update_manager::FakeUpdateManager fake_um_;
+};
+
+TEST_F(P2PDownloadActionTest, IsWrittenTo) {
+  if (!test_utils::IsXAttrSupported(FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+
+  SetupDownload(0);     // starting_offset
+  StartDownload(true);  // use_p2p_to_share
+
+  // Check the p2p file and its content matches what was sent.
+  string file_id = download_action_->p2p_file_id();
+  EXPECT_NE("", file_id);
+  EXPECT_EQ(data_.length(), p2p_manager_->FileGetSize(file_id));
+  EXPECT_EQ(data_.length(), p2p_manager_->FileGetExpectedSize(file_id));
+  string p2p_file_contents;
+  EXPECT_TRUE(ReadFileToString(p2p_manager_->FileGetPath(file_id),
+                               &p2p_file_contents));
+  EXPECT_EQ(data_, p2p_file_contents);
+}
+
+TEST_F(P2PDownloadActionTest, DeleteIfHoleExists) {
+  if (!test_utils::IsXAttrSupported(FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+
+  SetupDownload(1000);  // starting_offset
+  StartDownload(true);  // use_p2p_to_share
+
+  // DownloadAction should convey that the file is not being shared.
+  // and that we don't have any p2p files.
+  EXPECT_EQ(download_action_->p2p_file_id(), "");
+  EXPECT_EQ(p2p_manager_->CountSharedFiles(), 0);
+}
+
+TEST_F(P2PDownloadActionTest, CanAppend) {
+  if (!test_utils::IsXAttrSupported(FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+
+  SetupDownload(1000);  // starting_offset
+
+  // Prepare the file with existing data before starting to write to
+  // it via DownloadAction.
+  string file_id = utils::CalculateP2PFileId("1234hash", data_.length());
+  ASSERT_TRUE(p2p_manager_->FileShare(file_id, data_.length()));
+  string existing_data;
+  for (unsigned int i = 0; i < 1000; i++)
+    existing_data += '0' + (i % 10);
+  ASSERT_EQ(WriteFile(p2p_manager_->FileGetPath(file_id), existing_data.c_str(),
+                      1000), 1000);
+
+  StartDownload(true);  // use_p2p_to_share
+
+  // DownloadAction should convey the same file_id and the file should
+  // have the expected size.
+  EXPECT_EQ(download_action_->p2p_file_id(), file_id);
+  EXPECT_EQ(p2p_manager_->FileGetSize(file_id), data_.length());
+  EXPECT_EQ(p2p_manager_->FileGetExpectedSize(file_id), data_.length());
+  string p2p_file_contents;
+  // Check that the first 1000 bytes wasn't touched and that we
+  // appended the remaining as appropriate.
+  EXPECT_TRUE(ReadFileToString(p2p_manager_->FileGetPath(file_id),
+                               &p2p_file_contents));
+  EXPECT_EQ(existing_data, p2p_file_contents.substr(0, 1000));
+  EXPECT_EQ(data_.substr(1000), p2p_file_contents.substr(1000));
+}
+
+TEST_F(P2PDownloadActionTest, DeletePartialP2PFileIfResumingWithoutP2P) {
+  if (!test_utils::IsXAttrSupported(FilePath("/tmp"))) {
+    LOG(WARNING) << "Skipping test because /tmp does not support xattr. "
+                 << "Please update your system to support this feature.";
+    return;
+  }
+
+  SetupDownload(1000);  // starting_offset
+
+  // Prepare the file with all existing data before starting to write
+  // to it via DownloadAction.
+  string file_id = utils::CalculateP2PFileId("1234hash", data_.length());
+  ASSERT_TRUE(p2p_manager_->FileShare(file_id, data_.length()));
+  string existing_data;
+  for (unsigned int i = 0; i < 1000; i++)
+    existing_data += '0' + (i % 10);
+  ASSERT_EQ(WriteFile(p2p_manager_->FileGetPath(file_id), existing_data.c_str(),
+                      1000), 1000);
+
+  // Check that the file is there.
+  EXPECT_EQ(p2p_manager_->FileGetSize(file_id), 1000);
+  EXPECT_EQ(p2p_manager_->CountSharedFiles(), 1);
+
+  StartDownload(false);  // use_p2p_to_share
+
+  // DownloadAction should have deleted the p2p file. Check that it's gone.
+  EXPECT_EQ(p2p_manager_->FileGetSize(file_id), -1);
+  EXPECT_EQ(p2p_manager_->CountSharedFiles(), 0);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/extent_writer.cc b/payload_consumer/extent_writer.cc
new file mode 100644
index 0000000..5501e22
--- /dev/null
+++ b/payload_consumer/extent_writer.cc
@@ -0,0 +1,71 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/extent_writer.h"
+
+#include <errno.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <algorithm>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using std::min;
+
+namespace chromeos_update_engine {
+
+bool DirectExtentWriter::Write(const void* bytes, size_t count) {
+  if (count == 0)
+    return true;
+  const char* c_bytes = reinterpret_cast<const char*>(bytes);
+  size_t bytes_written = 0;
+  while (count - bytes_written > 0) {
+    TEST_AND_RETURN_FALSE(next_extent_index_ < extents_.size());
+    uint64_t bytes_remaining_next_extent =
+        extents_[next_extent_index_].num_blocks() * block_size_ -
+        extent_bytes_written_;
+    CHECK_NE(bytes_remaining_next_extent, static_cast<uint64_t>(0));
+    size_t bytes_to_write =
+        static_cast<size_t>(min(static_cast<uint64_t>(count - bytes_written),
+                                bytes_remaining_next_extent));
+    TEST_AND_RETURN_FALSE(bytes_to_write > 0);
+
+    if (extents_[next_extent_index_].start_block() != kSparseHole) {
+      const off64_t offset =
+          extents_[next_extent_index_].start_block() * block_size_ +
+          extent_bytes_written_;
+      TEST_AND_RETURN_FALSE_ERRNO(fd_->Seek(offset, SEEK_SET) !=
+                                  static_cast<off64_t>(-1));
+      TEST_AND_RETURN_FALSE(
+          utils::WriteAll(fd_, c_bytes + bytes_written, bytes_to_write));
+    }
+    bytes_written += bytes_to_write;
+    extent_bytes_written_ += bytes_to_write;
+    if (bytes_remaining_next_extent == bytes_to_write) {
+      // We filled this extent
+      CHECK_EQ(extent_bytes_written_,
+               extents_[next_extent_index_].num_blocks() * block_size_);
+      // move to next extent
+      extent_bytes_written_ = 0;
+      next_extent_index_++;
+    }
+  }
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/extent_writer.h b/payload_consumer/extent_writer.h
new file mode 100644
index 0000000..6484ebf
--- /dev/null
+++ b/payload_consumer/extent_writer.h
@@ -0,0 +1,134 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_EXTENT_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_EXTENT_WRITER_H_
+
+#include <vector>
+
+#include <base/logging.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/file_descriptor.h"
+#include "update_engine/update_metadata.pb.h"
+
+// ExtentWriter is an abstract class which synchronously writes to a given
+// file descriptor at the extents given.
+
+namespace chromeos_update_engine {
+
+class ExtentWriter {
+ public:
+  ExtentWriter() = default;
+  virtual ~ExtentWriter() {
+    LOG_IF(ERROR, !end_called_) << "End() not called on ExtentWriter.";
+  }
+
+  // Returns true on success.
+  virtual bool Init(FileDescriptorPtr fd,
+                    const std::vector<Extent>& extents,
+                    uint32_t block_size) = 0;
+
+  // Returns true on success.
+  virtual bool Write(const void* bytes, size_t count) = 0;
+
+  // Should be called when all writing is complete. Returns true on success.
+  // The fd is not closed. Caller is responsible for closing it.
+  bool End() {
+    end_called_ = true;
+    return EndImpl();
+  }
+  virtual bool EndImpl() = 0;
+ private:
+  bool end_called_{false};
+};
+
+// DirectExtentWriter is probably the simplest ExtentWriter implementation.
+// It writes the data directly into the extents.
+
+class DirectExtentWriter : public ExtentWriter {
+ public:
+  DirectExtentWriter() = default;
+  ~DirectExtentWriter() override = default;
+
+  bool Init(FileDescriptorPtr fd,
+            const std::vector<Extent>& extents,
+            uint32_t block_size) override {
+    fd_ = fd;
+    block_size_ = block_size;
+    extents_ = extents;
+    return true;
+  }
+  bool Write(const void* bytes, size_t count) override;
+  bool EndImpl() override { return true; }
+
+ private:
+  FileDescriptorPtr fd_{nullptr};
+
+  size_t block_size_{0};
+  // Bytes written into next_extent_index_ thus far
+  uint64_t extent_bytes_written_{0};
+  std::vector<Extent> extents_;
+  // The next call to write should correspond to extents_[next_extent_index_]
+  std::vector<Extent>::size_type next_extent_index_{0};
+};
+
+// Takes an underlying ExtentWriter to which all operations are delegated.
+// When End() is called, ZeroPadExtentWriter ensures that the total number
+// of bytes written is a multiple of block_size_. If not, it writes zeros
+// to pad as needed.
+
+class ZeroPadExtentWriter : public ExtentWriter {
+ public:
+  explicit ZeroPadExtentWriter(
+      std::unique_ptr<ExtentWriter> underlying_extent_writer)
+      : underlying_extent_writer_(std::move(underlying_extent_writer)) {}
+  ~ZeroPadExtentWriter() override = default;
+
+  bool Init(FileDescriptorPtr fd,
+            const std::vector<Extent>& extents,
+            uint32_t block_size) override {
+    block_size_ = block_size;
+    return underlying_extent_writer_->Init(fd, extents, block_size);
+  }
+  bool Write(const void* bytes, size_t count) override {
+    if (underlying_extent_writer_->Write(bytes, count)) {
+      bytes_written_mod_block_size_ += count;
+      bytes_written_mod_block_size_ %= block_size_;
+      return true;
+    }
+    return false;
+  }
+  bool EndImpl() override {
+    if (bytes_written_mod_block_size_) {
+      const size_t write_size = block_size_ - bytes_written_mod_block_size_;
+      brillo::Blob zeros(write_size, 0);
+      TEST_AND_RETURN_FALSE(underlying_extent_writer_->Write(zeros.data(),
+                                                             write_size));
+    }
+    return underlying_extent_writer_->End();
+  }
+
+ private:
+  std::unique_ptr<ExtentWriter> underlying_extent_writer_;
+  size_t block_size_{0};
+  size_t bytes_written_mod_block_size_{0};
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_EXTENT_WRITER_H_
diff --git a/payload_consumer/extent_writer_unittest.cc b/payload_consumer/extent_writer_unittest.cc
new file mode 100644
index 0000000..24ea5bf
--- /dev/null
+++ b/payload_consumer/extent_writer_unittest.cc
@@ -0,0 +1,270 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/extent_writer.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <brillo/make_unique_ptr.h>
+#include <brillo/secure_blob.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using chromeos_update_engine::test_utils::ExpectVectorsEq;
+using std::min;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+COMPILE_ASSERT(sizeof(off_t) == 8, off_t_not_64_bit);
+
+namespace {
+const char kPathTemplate[] = "./ExtentWriterTest-file.XXXXXX";
+const size_t kBlockSize = 4096;
+}
+
+class ExtentWriterTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    memcpy(path_, kPathTemplate, sizeof(kPathTemplate));
+    fd_.reset(new EintrSafeFileDescriptor);
+    int fd = mkstemp(path_);
+    ASSERT_TRUE(fd_->Open(path_, O_RDWR, 0600));
+    close(fd);
+  }
+  void TearDown() override {
+    fd_->Close();
+    unlink(path_);
+  }
+
+  // Writes data to an extent writer in 'chunk_size' chunks with
+  // the first chunk of size first_chunk_size. It calculates what the
+  // resultant file should look like and ensure that the extent writer
+  // wrote the file correctly.
+  void WriteAlignedExtents(size_t chunk_size, size_t first_chunk_size);
+  void TestZeroPad(bool aligned_size);
+
+  FileDescriptorPtr fd_;
+  char path_[sizeof(kPathTemplate)];
+};
+
+TEST_F(ExtentWriterTest, SimpleTest) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(1);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+
+  const string bytes = "1234";
+
+  DirectExtentWriter direct_writer;
+  EXPECT_TRUE(direct_writer.Init(fd_, extents, kBlockSize));
+  EXPECT_TRUE(direct_writer.Write(bytes.data(), bytes.size()));
+  EXPECT_TRUE(direct_writer.End());
+
+  EXPECT_EQ(kBlockSize + bytes.size(), utils::FileSize(path_));
+
+  brillo::Blob result_file;
+  EXPECT_TRUE(utils::ReadFile(path_, &result_file));
+
+  brillo::Blob expected_file(kBlockSize);
+  expected_file.insert(expected_file.end(),
+                       bytes.data(), bytes.data() + bytes.size());
+  ExpectVectorsEq(expected_file, result_file);
+}
+
+TEST_F(ExtentWriterTest, ZeroLengthTest) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(1);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+
+  DirectExtentWriter direct_writer;
+  EXPECT_TRUE(direct_writer.Init(fd_, extents, kBlockSize));
+  EXPECT_TRUE(direct_writer.Write(nullptr, 0));
+  EXPECT_TRUE(direct_writer.End());
+}
+
+TEST_F(ExtentWriterTest, OverflowExtentTest) {
+  WriteAlignedExtents(kBlockSize * 3, kBlockSize * 3);
+}
+
+TEST_F(ExtentWriterTest, UnalignedWriteTest) {
+  WriteAlignedExtents(7, 7);
+}
+
+TEST_F(ExtentWriterTest, LargeUnalignedWriteTest) {
+  WriteAlignedExtents(kBlockSize * 2, kBlockSize / 2);
+}
+
+void ExtentWriterTest::WriteAlignedExtents(size_t chunk_size,
+                                           size_t first_chunk_size) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(1);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+  extent.set_start_block(0);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+  extent.set_start_block(2);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+
+  brillo::Blob data(kBlockSize * 3);
+  test_utils::FillWithData(&data);
+
+  DirectExtentWriter direct_writer;
+  EXPECT_TRUE(direct_writer.Init(fd_, extents, kBlockSize));
+
+  size_t bytes_written = 0;
+  while (bytes_written < data.size()) {
+    size_t bytes_to_write = min(data.size() - bytes_written, chunk_size);
+    if (bytes_written == 0) {
+      bytes_to_write = min(data.size() - bytes_written, first_chunk_size);
+    }
+    EXPECT_TRUE(direct_writer.Write(&data[bytes_written], bytes_to_write));
+    bytes_written += bytes_to_write;
+  }
+  EXPECT_TRUE(direct_writer.End());
+
+  EXPECT_EQ(data.size(), utils::FileSize(path_));
+
+  brillo::Blob result_file;
+  EXPECT_TRUE(utils::ReadFile(path_, &result_file));
+
+  brillo::Blob expected_file;
+  expected_file.insert(expected_file.end(),
+                       data.begin() + kBlockSize,
+                       data.begin() + kBlockSize * 2);
+  expected_file.insert(expected_file.end(),
+                       data.begin(), data.begin() + kBlockSize);
+  expected_file.insert(expected_file.end(),
+                       data.begin() + kBlockSize * 2, data.end());
+  ExpectVectorsEq(expected_file, result_file);
+}
+
+TEST_F(ExtentWriterTest, ZeroPadNullTest) {
+  TestZeroPad(true);
+}
+
+TEST_F(ExtentWriterTest, ZeroPadFillTest) {
+  TestZeroPad(false);
+}
+
+void ExtentWriterTest::TestZeroPad(bool aligned_size) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(1);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+  extent.set_start_block(0);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+
+  brillo::Blob data(kBlockSize * 2);
+  test_utils::FillWithData(&data);
+
+  ZeroPadExtentWriter zero_pad_writer(
+      brillo::make_unique_ptr(new DirectExtentWriter()));
+
+  EXPECT_TRUE(zero_pad_writer.Init(fd_, extents, kBlockSize));
+  size_t bytes_to_write = data.size();
+  const size_t missing_bytes = (aligned_size ? 0 : 9);
+  bytes_to_write -= missing_bytes;
+  fd_->Seek(kBlockSize - missing_bytes, SEEK_SET);
+  EXPECT_EQ(3, fd_->Write("xxx", 3));
+  ASSERT_TRUE(zero_pad_writer.Write(data.data(), bytes_to_write));
+  EXPECT_TRUE(zero_pad_writer.End());
+
+  EXPECT_EQ(data.size(), utils::FileSize(path_));
+
+  brillo::Blob result_file;
+  EXPECT_TRUE(utils::ReadFile(path_, &result_file));
+
+  brillo::Blob expected_file;
+  expected_file.insert(expected_file.end(),
+                       data.begin() + kBlockSize,
+                       data.begin() + kBlockSize * 2);
+  expected_file.insert(expected_file.end(),
+                       data.begin(), data.begin() + kBlockSize);
+  if (missing_bytes) {
+    memset(&expected_file[kBlockSize - missing_bytes], 0, missing_bytes);
+  }
+
+  ExpectVectorsEq(expected_file, result_file);
+}
+
+TEST_F(ExtentWriterTest, SparseFileTest) {
+  vector<Extent> extents;
+  Extent extent;
+  extent.set_start_block(1);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+  extent.set_start_block(kSparseHole);
+  extent.set_num_blocks(2);
+  extents.push_back(extent);
+  extent.set_start_block(0);
+  extent.set_num_blocks(1);
+  extents.push_back(extent);
+  const int block_count = 4;
+  const int on_disk_count = 2;
+
+  brillo::Blob data(17);
+  test_utils::FillWithData(&data);
+
+  DirectExtentWriter direct_writer;
+  EXPECT_TRUE(direct_writer.Init(fd_, extents, kBlockSize));
+
+  size_t bytes_written = 0;
+  while (bytes_written < (block_count * kBlockSize)) {
+    size_t bytes_to_write = min(block_count * kBlockSize - bytes_written,
+                                data.size());
+    EXPECT_TRUE(direct_writer.Write(data.data(), bytes_to_write));
+    bytes_written += bytes_to_write;
+  }
+  EXPECT_TRUE(direct_writer.End());
+
+  // check file size, then data inside
+  ASSERT_EQ(2 * kBlockSize, utils::FileSize(path_));
+
+  brillo::Blob resultant_data;
+  EXPECT_TRUE(utils::ReadFile(path_, &resultant_data));
+
+  // Create expected data
+  brillo::Blob expected_data(on_disk_count * kBlockSize);
+  brillo::Blob big(block_count * kBlockSize);
+  for (brillo::Blob::size_type i = 0; i < big.size(); i++) {
+    big[i] = data[i % data.size()];
+  }
+  memcpy(&expected_data[kBlockSize], &big[0], kBlockSize);
+  memcpy(&expected_data[0], &big[3 * kBlockSize], kBlockSize);
+  ExpectVectorsEq(expected_data, resultant_data);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/fake_extent_writer.h b/payload_consumer/fake_extent_writer.h
new file mode 100644
index 0000000..762c6d5
--- /dev/null
+++ b/payload_consumer/fake_extent_writer.h
@@ -0,0 +1,71 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_FAKE_EXTENT_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_FAKE_EXTENT_WRITER_H_
+
+#include <memory>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_consumer/extent_writer.h"
+
+namespace chromeos_update_engine {
+
+// FakeExtentWriter is a concrete ExtentWriter subclass that keeps track of all
+// the written data, useful for testing.
+class FakeExtentWriter : public ExtentWriter {
+ public:
+  FakeExtentWriter() = default;
+  ~FakeExtentWriter() override = default;
+
+  // ExtentWriter overrides.
+  bool Init(FileDescriptorPtr /* fd */,
+            const std::vector<Extent>& /* extents */,
+            uint32_t /* block_size */) override {
+    init_called_ = true;
+    return true;
+  };
+  bool Write(const void* bytes, size_t count) override {
+    if (!init_called_ || end_called_)
+      return false;
+    written_data_.insert(written_data_.end(),
+                         reinterpret_cast<const uint8_t*>(bytes),
+                         reinterpret_cast<const uint8_t*>(bytes) + count);
+    return true;
+  }
+  bool EndImpl() override {
+    end_called_ = true;
+    return true;
+  }
+
+  // Fake methods.
+  bool InitCalled() { return init_called_; }
+  bool EndCalled() { return end_called_; }
+  brillo::Blob WrittenData() { return written_data_; }
+
+ private:
+  bool init_called_{false};
+  bool end_called_{false};
+  brillo::Blob written_data_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeExtentWriter);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_FAKE_EXTENT_WRITER_H_
diff --git a/payload_consumer/file_descriptor.cc b/payload_consumer/file_descriptor.cc
new file mode 100644
index 0000000..f26be28
--- /dev/null
+++ b/payload_consumer/file_descriptor.cc
@@ -0,0 +1,116 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/file_descriptor.h"
+
+#include <fcntl.h>
+#include <linux/fs.h>
+#include <sys/ioctl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <base/posix/eintr_wrapper.h>
+
+namespace chromeos_update_engine {
+
+bool EintrSafeFileDescriptor::Open(const char* path, int flags, mode_t mode) {
+  CHECK_EQ(fd_, -1);
+  return ((fd_ = HANDLE_EINTR(open(path, flags, mode))) >= 0);
+}
+
+bool EintrSafeFileDescriptor::Open(const char* path, int flags) {
+  CHECK_EQ(fd_, -1);
+  return ((fd_ = HANDLE_EINTR(open(path, flags))) >= 0);
+}
+
+ssize_t EintrSafeFileDescriptor::Read(void* buf, size_t count) {
+  CHECK_GE(fd_, 0);
+  return HANDLE_EINTR(read(fd_, buf, count));
+}
+
+ssize_t EintrSafeFileDescriptor::Write(const void* buf, size_t count) {
+  CHECK_GE(fd_, 0);
+
+  // Attempt repeated writes, as long as some progress is being made.
+  char* char_buf = const_cast<char*>(reinterpret_cast<const char*>(buf));
+  ssize_t written = 0;
+  while (count > 0) {
+    ssize_t ret = HANDLE_EINTR(write(fd_, char_buf, count));
+
+    // Fail on either an error or no progress.
+    if (ret <= 0)
+      return (written ? written : ret);
+    written += ret;
+    count -= ret;
+    char_buf += ret;
+  }
+  return written;
+}
+
+off64_t EintrSafeFileDescriptor::Seek(off64_t offset, int whence) {
+  CHECK_GE(fd_, 0);
+  return lseek64(fd_, offset, whence);
+}
+
+bool EintrSafeFileDescriptor::BlkIoctl(int request,
+                                       uint64_t start,
+                                       uint64_t length,
+                                       int* result) {
+  DCHECK(request == BLKDISCARD || request == BLKZEROOUT ||
+         request == BLKSECDISCARD);
+  // On some devices, the BLKDISCARD will actually read back as zeros, instead
+  // of "undefined" data. The BLKDISCARDZEROES ioctl tells whether that's the
+  // case, so we issue a BLKDISCARD in those cases to speed up the writes.
+  unsigned int arg;
+  if (request == BLKZEROOUT && ioctl(fd_, BLKDISCARDZEROES, &arg) == 0 && arg)
+    request = BLKDISCARD;
+
+  // Ensure the |fd_| is in O_DIRECT mode during this operation, so the write
+  // cache for this region is invalidated. This is required since otherwise
+  // reading back this region could consume stale data from the cache.
+  int flags = fcntl(fd_, F_GETFL, 0);
+  if (flags == -1) {
+    PLOG(WARNING) << "Couldn't get flags on fd " << fd_;
+    return false;
+  }
+  if ((flags & O_DIRECT) == 0 && fcntl(fd_, F_SETFL, flags | O_DIRECT) == -1) {
+    PLOG(WARNING) << "Couldn't set O_DIRECT on fd " << fd_;
+    return false;
+  }
+
+  uint64_t range[2] = {start, length};
+  *result = ioctl(fd_, request, range);
+
+  if ((flags & O_DIRECT) == 0 && fcntl(fd_, F_SETFL, flags) == -1) {
+    PLOG(WARNING) << "Couldn't remove O_DIRECT on fd " << fd_;
+    return false;
+  }
+  return true;
+}
+
+bool EintrSafeFileDescriptor::Close() {
+  CHECK_GE(fd_, 0);
+  if (IGNORE_EINTR(close(fd_)))
+    return false;
+  Reset();
+  return true;
+}
+
+void EintrSafeFileDescriptor::Reset() {
+  fd_ = -1;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/file_descriptor.h b/payload_consumer/file_descriptor.h
new file mode 100644
index 0000000..3c15415
--- /dev/null
+++ b/payload_consumer/file_descriptor.h
@@ -0,0 +1,141 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_DESCRIPTOR_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_DESCRIPTOR_H_
+
+#include <errno.h>
+#include <memory>
+#include <sys/types.h>
+
+#include <base/logging.h>
+
+// Abstraction for managing opening, reading, writing and closing of file
+// descriptors. This includes an abstract class and one standard implementation
+// based on POSIX system calls.
+//
+// TODO(garnold) this class is modeled after (and augments the functionality of)
+// the FileWriter class; ultimately, the latter should be replaced by the former
+// throughout the codebase.  A few deviations from the original FileWriter:
+//
+// * Providing two flavors of Open()
+//
+// * A FileDescriptor is reusable and can be used to read/write multiple files
+//   as long as open/close preconditions are respected.
+//
+// * Write() returns the number of bytes written: this appears to be more useful
+//   for clients, who may wish to retry or otherwise do something useful with
+//   the remaining data that was not written.
+//
+// * Provides a Reset() method, which will force to abandon a currently open
+//   file descriptor and allow opening another file, without necessarily
+//   properly closing the old one. This may be useful in cases where a "closer"
+//   class does not care whether Close() was successful, but may need to reuse
+//   the same file descriptor again.
+
+namespace chromeos_update_engine {
+
+class FileDescriptor;
+using FileDescriptorPtr = std::shared_ptr<FileDescriptor>;
+
+// An abstract class defining the file descriptor API.
+class FileDescriptor {
+ public:
+  FileDescriptor() {}
+  virtual ~FileDescriptor() {}
+
+  // Opens a file descriptor. The descriptor must be in the closed state prior
+  // to this call. Returns true on success, false otherwise. Specific
+  // implementations may set errno accordingly.
+  virtual bool Open(const char* path, int flags, mode_t mode) = 0;
+  virtual bool Open(const char* path, int flags) = 0;
+
+  // Reads from a file descriptor up to a given count. The descriptor must be
+  // open prior to this call. Returns the number of bytes read, or -1 on error.
+  // Specific implementations may set errno accordingly.
+  virtual ssize_t Read(void* buf, size_t count) = 0;
+
+  // Writes to a file descriptor. The descriptor must be open prior to this
+  // call. Returns the number of bytes written, or -1 if an error occurred and
+  // no bytes were written. Specific implementations may set errno accordingly.
+  virtual ssize_t Write(const void* buf, size_t count) = 0;
+
+  // Seeks to an offset. Returns the resulting offset location as measured in
+  // bytes from the beginning. On error, return -1. Specific implementations
+  // may set errno accordingly.
+  virtual off64_t Seek(off64_t offset, int whence) = 0;
+
+  // Runs a ioctl() on the file descriptor if supported. Returns whether
+  // the operation is supported. The |request| can be one of BLKDISCARD,
+  // BLKZEROOUT and BLKSECDISCARD to discard, write zeros or securely discard
+  // the blocks. These ioctls accept a range of bytes (|start| and |length|)
+  // over which they perform the operation. The return value from the ioctl is
+  // stored in |result|.
+  virtual bool BlkIoctl(int request,
+                        uint64_t start,
+                        uint64_t length,
+                        int* result) = 0;
+
+  // Closes a file descriptor. The descriptor must be open prior to this call.
+  // Returns true on success, false otherwise. Specific implementations may set
+  // errno accordingly.
+  virtual bool Close() = 0;
+
+  // Resets the file descriptor, abandoning a currently open file and returning
+  // the descriptor to the closed state.
+  virtual void Reset() = 0;
+
+  // Indicates whether or not an implementation sets meaningful errno.
+  virtual bool IsSettingErrno() = 0;
+
+  // Indicates whether the descriptor is currently open.
+  virtual bool IsOpen() = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(FileDescriptor);
+};
+
+// A simple EINTR-immune wrapper implementation around standard system calls.
+class EintrSafeFileDescriptor : public FileDescriptor {
+ public:
+  EintrSafeFileDescriptor() : fd_(-1) {}
+
+  // Interface methods.
+  bool Open(const char* path, int flags, mode_t mode) override;
+  bool Open(const char* path, int flags) override;
+  ssize_t Read(void* buf, size_t count) override;
+  ssize_t Write(const void* buf, size_t count) override;
+  off64_t Seek(off64_t offset, int whence) override;
+  bool BlkIoctl(int request,
+                uint64_t start,
+                uint64_t length,
+                int* result) override;
+  bool Close() override;
+  void Reset() override;
+  bool IsSettingErrno() override {
+    return true;
+  }
+  bool IsOpen() override {
+    return (fd_ >= 0);
+  }
+
+ protected:
+  int fd_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_DESCRIPTOR_H_
diff --git a/payload_consumer/file_writer.cc b/payload_consumer/file_writer.cc
new file mode 100644
index 0000000..d280ddb
--- /dev/null
+++ b/payload_consumer/file_writer.cc
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/file_writer.h"
+
+#include <errno.h>
+
+namespace chromeos_update_engine {
+
+int DirectFileWriter::Open(const char* path, int flags, mode_t mode) {
+  CHECK_EQ(fd_, -1);
+  fd_ = open(path, flags, mode);
+  if (fd_ < 0)
+    return -errno;
+  return 0;
+}
+
+bool DirectFileWriter::Write(const void* bytes, size_t count) {
+  CHECK_GE(fd_, 0);
+  const char* char_bytes = reinterpret_cast<const char*>(bytes);
+
+  size_t bytes_written = 0;
+  while (bytes_written < count) {
+    ssize_t rc = write(fd_, char_bytes + bytes_written,
+                       count - bytes_written);
+    if (rc < 0)
+      return false;
+    bytes_written += rc;
+  }
+  CHECK_EQ(bytes_written, count);
+  return bytes_written == count;
+}
+
+int DirectFileWriter::Close() {
+  CHECK_GE(fd_, 0);
+  int rc = close(fd_);
+
+  // This can be any negative number that's not -1. This way, this FileWriter
+  // won't be used again for another file.
+  fd_ = -2;
+
+  if (rc < 0)
+    return -errno;
+  return rc;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/file_writer.h b/payload_consumer/file_writer.h
new file mode 100644
index 0000000..96ebde6
--- /dev/null
+++ b/payload_consumer/file_writer.h
@@ -0,0 +1,103 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_WRITER_H_
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <base/logging.h>
+
+#include "update_engine/common/error_code.h"
+#include "update_engine/common/utils.h"
+
+// FileWriter is a class that is used to (synchronously, for now) write to
+// a file. This file is a thin wrapper around open/write/close system calls,
+// but provides and interface that can be customized by subclasses that wish
+// to filter the data.
+
+namespace chromeos_update_engine {
+
+class FileWriter {
+ public:
+  FileWriter() {}
+  virtual ~FileWriter() {}
+
+  // Wrapper around write. Returns true if all requested bytes
+  // were written, or false on any error, regardless of progress.
+  virtual bool Write(const void* bytes, size_t count) = 0;
+
+  // Same as the Write method above but returns a detailed |error| code
+  // in addition if the returned value is false. By default this method
+  // returns kActionExitDownloadWriteError as the error code, but subclasses
+  // can override if they wish to return more specific error codes.
+  virtual bool Write(const void* bytes,
+                     size_t count,
+                     ErrorCode* error) {
+     *error = ErrorCode::kDownloadWriteError;
+     return Write(bytes, count);
+  }
+
+  // Wrapper around close. Returns 0 on success or -errno on error.
+  virtual int Close() = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(FileWriter);
+};
+
+// Direct file writer is probably the simplest FileWriter implementation.
+// It calls the system calls directly.
+
+class DirectFileWriter : public FileWriter {
+ public:
+  DirectFileWriter() = default;
+
+  // FileWriter overrides.
+  bool Write(const void* bytes, size_t count) override;
+  int Close() override;
+
+  // Wrapper around open. Returns 0 on success or -errno on error.
+  int Open(const char* path, int flags, mode_t mode);
+
+  int fd() const { return fd_; }
+
+ private:
+  int fd_{-1};
+
+  DISALLOW_COPY_AND_ASSIGN(DirectFileWriter);
+};
+
+class ScopedFileWriterCloser {
+ public:
+  explicit ScopedFileWriterCloser(FileWriter* writer) : writer_(writer) {}
+  ~ScopedFileWriterCloser() {
+    int err = writer_->Close();
+    if (err)
+      LOG(ERROR) << "FileWriter::Close failed: "
+                 << utils::ErrnoNumberAsString(-err);
+  }
+ private:
+  FileWriter* writer_;
+
+  DISALLOW_COPY_AND_ASSIGN(ScopedFileWriterCloser);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_FILE_WRITER_H_
diff --git a/payload_consumer/file_writer_unittest.cc b/payload_consumer/file_writer_unittest.cc
new file mode 100644
index 0000000..debb4c3
--- /dev/null
+++ b/payload_consumer/file_writer_unittest.cc
@@ -0,0 +1,79 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_consumer/file_writer.h"
+
+#include <errno.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class FileWriterTest : public ::testing::Test { };
+
+TEST(FileWriterTest, SimpleTest) {
+  // Create a uniquely named file for testing.
+  string path;
+  ASSERT_TRUE(utils::MakeTempFile("FileWriterTest-XXXXXX", &path, nullptr));
+  ScopedPathUnlinker path_unlinker(path);
+
+  DirectFileWriter file_writer;
+  EXPECT_EQ(0, file_writer.Open(path.c_str(),
+                                O_CREAT | O_LARGEFILE | O_TRUNC | O_WRONLY,
+                                0644));
+  EXPECT_TRUE(file_writer.Write("test", 4));
+  brillo::Blob actual_data;
+  EXPECT_TRUE(utils::ReadFile(path, &actual_data));
+
+  EXPECT_FALSE(memcmp("test", actual_data.data(), actual_data.size()));
+  EXPECT_EQ(0, file_writer.Close());
+}
+
+TEST(FileWriterTest, ErrorTest) {
+  DirectFileWriter file_writer;
+  const string path("/tmp/ENOENT/FileWriterTest");
+  EXPECT_EQ(-ENOENT, file_writer.Open(path.c_str(),
+                                      O_CREAT | O_LARGEFILE | O_TRUNC, 0644));
+}
+
+TEST(FileWriterTest, WriteErrorTest) {
+  // Create a uniquely named file for testing.
+  string path;
+  ASSERT_TRUE(utils::MakeTempFile("FileWriterTest-XXXXXX", &path, nullptr));
+  ScopedPathUnlinker path_unlinker(path);
+
+  DirectFileWriter file_writer;
+  EXPECT_EQ(0, file_writer.Open(path.c_str(),
+                                O_CREAT | O_LARGEFILE | O_TRUNC | O_RDONLY,
+                                0644));
+  EXPECT_FALSE(file_writer.Write("x", 1));
+  EXPECT_EQ(0, file_writer.Close());
+}
+
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/filesystem_verifier_action.cc b/payload_consumer/filesystem_verifier_action.cc
new file mode 100644
index 0000000..8530d37
--- /dev/null
+++ b/payload_consumer/filesystem_verifier_action.cc
@@ -0,0 +1,287 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/filesystem_verifier_action.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <algorithm>
+#include <cstdlib>
+#include <string>
+
+#include <base/bind.h>
+#include <brillo/streams/file_stream.h>
+
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace {
+const off_t kReadFileBufferSize = 128 * 1024;
+}  // namespace
+
+FilesystemVerifierAction::FilesystemVerifierAction(
+    const BootControlInterface* boot_control,
+    VerifierMode verifier_mode)
+    : verifier_mode_(verifier_mode),
+      boot_control_(boot_control) {}
+
+void FilesystemVerifierAction::PerformAction() {
+  // Will tell the ActionProcessor we've failed if we return.
+  ScopedActionCompleter abort_action_completer(processor_, this);
+
+  if (!HasInputObject()) {
+    LOG(ERROR) << "FilesystemVerifierAction missing input object.";
+    return;
+  }
+  install_plan_ = GetInputObject();
+
+  // For delta updates (major version 1) we need to populate the source
+  // partition hash if not pre-populated.
+  if (!install_plan_.is_full_update && install_plan_.partitions.empty() &&
+      verifier_mode_ == VerifierMode::kComputeSourceHash &&
+      DeltaPerformer::kSupportedMinorPayloadVersion <
+          kOpSrcHashMinorPayloadVersion) {
+    LOG(INFO) << "Using legacy partition names.";
+    InstallPlan::Partition part;
+    string part_path;
+
+    part.name = kLegacyPartitionNameRoot;
+    if (!boot_control_->GetPartitionDevice(
+        part.name, install_plan_.source_slot, &part_path))
+      return;
+    int block_count = 0, block_size = 0;
+    if (utils::GetFilesystemSize(part_path, &block_count, &block_size)) {
+      part.source_size = static_cast<int64_t>(block_count) * block_size;
+      LOG(INFO) << "Partition " << part.name << " size: " << part.source_size
+                << " bytes (" << block_count << "x" << block_size << ").";
+    }
+    install_plan_.partitions.push_back(part);
+
+    part.name = kLegacyPartitionNameKernel;
+    if (!boot_control_->GetPartitionDevice(
+        part.name, install_plan_.source_slot, &part_path))
+      return;
+    off_t kernel_part_size = utils::FileSize(part_path);
+    if (kernel_part_size < 0)
+      return;
+    LOG(INFO) << "Partition " << part.name << " size: " << kernel_part_size
+              << " bytes.";
+    part.source_size = kernel_part_size;
+    install_plan_.partitions.push_back(part);
+  }
+
+  if (install_plan_.partitions.empty()) {
+    LOG(INFO) << "No partitions to verify.";
+    if (HasOutputPipe())
+      SetOutputObject(install_plan_);
+    abort_action_completer.set_code(ErrorCode::kSuccess);
+    return;
+  }
+
+  StartPartitionHashing();
+  abort_action_completer.set_should_complete(false);
+}
+
+void FilesystemVerifierAction::TerminateProcessing() {
+  cancelled_ = true;
+  Cleanup(ErrorCode::kSuccess);  // error code is ignored if canceled_ is true.
+}
+
+bool FilesystemVerifierAction::IsCleanupPending() const {
+  return src_stream_ != nullptr;
+}
+
+void FilesystemVerifierAction::Cleanup(ErrorCode code) {
+  src_stream_.reset();
+  // This memory is not used anymore.
+  buffer_.clear();
+
+  if (cancelled_)
+    return;
+  if (code == ErrorCode::kSuccess && HasOutputPipe())
+    SetOutputObject(install_plan_);
+  processor_->ActionComplete(this, code);
+}
+
+void FilesystemVerifierAction::StartPartitionHashing() {
+  if (partition_index_ == install_plan_.partitions.size()) {
+    // We never called this action with kVerifySourceHash directly, if we are in
+    // this mode, it means the target partition verification has failed, so we
+    // should set the error code to reflect the error in target.
+    if (verifier_mode_ == VerifierMode::kVerifySourceHash)
+      Cleanup(ErrorCode::kNewRootfsVerificationError);
+    else
+      Cleanup(ErrorCode::kSuccess);
+    return;
+  }
+  InstallPlan::Partition& partition =
+      install_plan_.partitions[partition_index_];
+
+  string part_path;
+  switch (verifier_mode_) {
+    case VerifierMode::kComputeSourceHash:
+    case VerifierMode::kVerifySourceHash:
+      boot_control_->GetPartitionDevice(
+          partition.name, install_plan_.source_slot, &part_path);
+      remaining_size_ = partition.source_size;
+      break;
+    case VerifierMode::kVerifyTargetHash:
+      boot_control_->GetPartitionDevice(
+          partition.name, install_plan_.target_slot, &part_path);
+      remaining_size_ = partition.target_size;
+      break;
+  }
+  LOG(INFO) << "Hashing partition " << partition_index_ << " ("
+            << partition.name << ") on device " << part_path;
+  if (part_path.empty())
+    return Cleanup(ErrorCode::kFilesystemVerifierError);
+
+  brillo::ErrorPtr error;
+  src_stream_ = brillo::FileStream::Open(
+      base::FilePath(part_path),
+      brillo::Stream::AccessMode::READ,
+      brillo::FileStream::Disposition::OPEN_EXISTING,
+      &error);
+
+  if (!src_stream_) {
+    LOG(ERROR) << "Unable to open " << part_path << " for reading";
+    return Cleanup(ErrorCode::kFilesystemVerifierError);
+  }
+
+  buffer_.resize(kReadFileBufferSize);
+  read_done_ = false;
+  hasher_.reset(new HashCalculator());
+
+  // Start the first read.
+  ScheduleRead();
+}
+
+void FilesystemVerifierAction::ScheduleRead() {
+  size_t bytes_to_read = std::min(static_cast<int64_t>(buffer_.size()),
+                                  remaining_size_);
+  if (!bytes_to_read) {
+    OnReadDoneCallback(0);
+    return;
+  }
+
+  bool read_async_ok = src_stream_->ReadAsync(
+    buffer_.data(),
+    bytes_to_read,
+    base::Bind(&FilesystemVerifierAction::OnReadDoneCallback,
+               base::Unretained(this)),
+    base::Bind(&FilesystemVerifierAction::OnReadErrorCallback,
+               base::Unretained(this)),
+    nullptr);
+
+  if (!read_async_ok) {
+    LOG(ERROR) << "Unable to schedule an asynchronous read from the stream.";
+    Cleanup(ErrorCode::kError);
+  }
+}
+
+void FilesystemVerifierAction::OnReadDoneCallback(size_t bytes_read) {
+  if (bytes_read == 0) {
+    read_done_ = true;
+  } else {
+    remaining_size_ -= bytes_read;
+    CHECK(!read_done_);
+    if (!hasher_->Update(buffer_.data(), bytes_read)) {
+      LOG(ERROR) << "Unable to update the hash.";
+      Cleanup(ErrorCode::kError);
+      return;
+    }
+  }
+
+  // We either terminate the current partition or have more data to read.
+  if (cancelled_)
+    return Cleanup(ErrorCode::kError);
+
+  if (read_done_ || remaining_size_ == 0) {
+    if (remaining_size_ != 0) {
+      LOG(ERROR) << "Failed to read the remaining " << remaining_size_
+                 << " bytes from partition "
+                 << install_plan_.partitions[partition_index_].name;
+      return Cleanup(ErrorCode::kFilesystemVerifierError);
+    }
+    return FinishPartitionHashing();
+  }
+  ScheduleRead();
+}
+
+void FilesystemVerifierAction::OnReadErrorCallback(
+      const brillo::Error* error) {
+  // TODO(deymo): Transform the read-error into an specific ErrorCode.
+  LOG(ERROR) << "Asynchronous read failed.";
+  Cleanup(ErrorCode::kError);
+}
+
+void FilesystemVerifierAction::FinishPartitionHashing() {
+  if (!hasher_->Finalize()) {
+    LOG(ERROR) << "Unable to finalize the hash.";
+    return Cleanup(ErrorCode::kError);
+  }
+  InstallPlan::Partition& partition =
+      install_plan_.partitions[partition_index_];
+  LOG(INFO) << "Hash of " << partition.name << ": " << hasher_->hash();
+
+  switch (verifier_mode_) {
+    case VerifierMode::kComputeSourceHash:
+      partition.source_hash = hasher_->raw_hash();
+      partition_index_++;
+      break;
+    case VerifierMode::kVerifyTargetHash:
+      if (partition.target_hash != hasher_->raw_hash()) {
+        LOG(ERROR) << "New '" << partition.name
+                   << "' partition verification failed.";
+        if (DeltaPerformer::kSupportedMinorPayloadVersion <
+            kOpSrcHashMinorPayloadVersion)
+          return Cleanup(ErrorCode::kNewRootfsVerificationError);
+        // If we support per-operation source hash, then we skipped source
+        // filesystem verification, now that the target partition does not
+        // match, we need to switch to kVerifySourceHash mode to check if it's
+        // because the source partition does not match either.
+        verifier_mode_ = VerifierMode::kVerifySourceHash;
+        partition_index_ = 0;
+      } else {
+        partition_index_++;
+      }
+      break;
+    case VerifierMode::kVerifySourceHash:
+      if (partition.source_hash != hasher_->raw_hash()) {
+        LOG(ERROR) << "Old '" << partition.name
+                   << "' partition verification failed.";
+        return Cleanup(ErrorCode::kDownloadStateInitializationError);
+      }
+      partition_index_++;
+      break;
+  }
+  // Start hashing the next partition, if any.
+  hasher_.reset();
+  buffer_.clear();
+  src_stream_->CloseBlocking(nullptr);
+  StartPartitionHashing();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/filesystem_verifier_action.h b/payload_consumer/filesystem_verifier_action.h
new file mode 100644
index 0000000..94f1b4e
--- /dev/null
+++ b/payload_consumer/filesystem_verifier_action.h
@@ -0,0 +1,130 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_FILESYSTEM_VERIFIER_ACTION_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_FILESYSTEM_VERIFIER_ACTION_H_
+
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <string>
+#include <vector>
+
+#include <brillo/streams/stream.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/payload_consumer/install_plan.h"
+
+// This action will hash all the partitions of a single slot involved in the
+// update (either source or target slot). The hashes are then either stored in
+// the InstallPlan (for source partitions) or verified against it (for target
+// partitions).
+
+namespace chromeos_update_engine {
+
+// The mode we are running the FilesystemVerifier on. On kComputeSourceHash mode
+// it computes the source_hash of all the partitions in the InstallPlan, based
+// on the already populated source_size values. On kVerifyTargetHash it computes
+// the hash on the target partitions based on the already populated size and
+// verifies it matches the one in the target_hash in the InstallPlan.
+enum class VerifierMode {
+  kComputeSourceHash,
+  kVerifyTargetHash,
+  kVerifySourceHash,
+};
+
+class FilesystemVerifierAction : public InstallPlanAction {
+ public:
+  FilesystemVerifierAction(const BootControlInterface* boot_control,
+                           VerifierMode verifier_mode);
+
+  void PerformAction() override;
+  void TerminateProcessing() override;
+
+  // Used for testing. Return true if Cleanup() has not yet been called due
+  // to a callback upon the completion or cancellation of the verifier action.
+  // A test should wait until IsCleanupPending() returns false before
+  // terminating the main loop.
+  bool IsCleanupPending() const;
+
+  // Debugging/logging
+  static std::string StaticType() { return "FilesystemVerifierAction"; }
+  std::string Type() const override { return StaticType(); }
+
+ private:
+  friend class FilesystemVerifierActionTest;
+  FRIEND_TEST(FilesystemVerifierActionTest,
+              RunAsRootDetermineFilesystemSizeTest);
+
+  // Starts the hashing of the current partition. If there aren't any partitions
+  // remaining to be hashed, if finishes the action.
+  void StartPartitionHashing();
+
+  // Schedules the asynchronous read of the filesystem.
+  void ScheduleRead();
+
+  // Called from the main loop when a single read from |src_stream_| succeeds or
+  // fails, calling OnReadDoneCallback() and OnReadErrorCallback() respectively.
+  void OnReadDoneCallback(size_t bytes_read);
+  void OnReadErrorCallback(const brillo::Error* error);
+
+  // When the read is done, finalize the hash checking of the current partition
+  // and continue checking the next one.
+  void FinishPartitionHashing();
+
+  // Cleans up all the variables we use for async operations and tells the
+  // ActionProcessor we're done w/ |code| as passed in. |cancelled_| should be
+  // true if TerminateProcessing() was called.
+  void Cleanup(ErrorCode code);
+
+  // The type of the partition that we are verifying.
+  VerifierMode verifier_mode_;
+
+  // The BootControlInterface used to get the partitions based on the slots.
+  const BootControlInterface* const boot_control_;
+
+  // The index in the install_plan_.partitions vector of the partition currently
+  // being hashed.
+  size_t partition_index_{0};
+
+  // If not null, the FileStream used to read from the device.
+  brillo::StreamPtr src_stream_;
+
+  // Buffer for storing data we read.
+  brillo::Blob buffer_;
+
+  bool read_done_{false};  // true if reached EOF on the input stream.
+  bool cancelled_{false};  // true if the action has been cancelled.
+
+  // The install plan we're passed in via the input pipe.
+  InstallPlan install_plan_;
+
+  // Calculates the hash of the data.
+  std::unique_ptr<HashCalculator> hasher_;
+
+  // Reads and hashes this many bytes from the head of the input stream. This
+  // field is initialized from the corresponding InstallPlan::Partition size,
+  // when the partition starts to be hashed.
+  int64_t remaining_size_{0};
+
+  DISALLOW_COPY_AND_ASSIGN(FilesystemVerifierAction);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_FILESYSTEM_VERIFIER_ACTION_H_
diff --git a/payload_consumer/filesystem_verifier_action_unittest.cc b/payload_consumer/filesystem_verifier_action_unittest.cc
new file mode 100644
index 0000000..0b6232b
--- /dev/null
+++ b/payload_consumer/filesystem_verifier_action_unittest.cc
@@ -0,0 +1,386 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/filesystem_verifier_action.h"
+
+#include <fcntl.h>
+
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/posix/eintr_wrapper.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using brillo::MessageLoop;
+using std::set;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class FilesystemVerifierActionTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+  }
+
+  void TearDown() override {
+    EXPECT_EQ(0, brillo::MessageLoopRunMaxIterations(&loop_, 1));
+  }
+
+  // Returns true iff test has completed successfully.
+  bool DoTest(bool terminate_early,
+              bool hash_fail,
+              VerifierMode verifier_mode);
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  FakeBootControl fake_boot_control_;
+};
+
+class FilesystemVerifierActionTestDelegate : public ActionProcessorDelegate {
+ public:
+  explicit FilesystemVerifierActionTestDelegate(
+      FilesystemVerifierAction* action)
+      : action_(action), ran_(false), code_(ErrorCode::kError) {}
+  void ExitMainLoop() {
+    // We need to wait for the Action to call Cleanup.
+    if (action_->IsCleanupPending()) {
+      LOG(INFO) << "Waiting for Cleanup() to be called.";
+      MessageLoop::current()->PostDelayedTask(
+          FROM_HERE,
+          base::Bind(&FilesystemVerifierActionTestDelegate::ExitMainLoop,
+                     base::Unretained(this)),
+          base::TimeDelta::FromMilliseconds(100));
+    } else {
+      MessageLoop::current()->BreakLoop();
+    }
+  }
+  void ProcessingDone(const ActionProcessor* processor, ErrorCode code) {
+    ExitMainLoop();
+  }
+  void ProcessingStopped(const ActionProcessor* processor) {
+    ExitMainLoop();
+  }
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) {
+    if (action->Type() == FilesystemVerifierAction::StaticType()) {
+      ran_ = true;
+      code_ = code;
+    }
+  }
+  bool ran() const { return ran_; }
+  ErrorCode code() const { return code_; }
+
+ private:
+  FilesystemVerifierAction* action_;
+  bool ran_;
+  ErrorCode code_;
+};
+
+void StartProcessorInRunLoop(ActionProcessor* processor,
+                             FilesystemVerifierAction* filesystem_copier_action,
+                             bool terminate_early) {
+  processor->StartProcessing();
+  if (terminate_early) {
+    EXPECT_NE(nullptr, filesystem_copier_action);
+    processor->StopProcessing();
+  }
+}
+
+// TODO(garnold) Temporarily disabling this test, see chromium-os:31082 for
+// details; still trying to track down the root cause for these rare write
+// failures and whether or not they are due to the test setup or an inherent
+// issue with the chroot environment, library versions we use, etc.
+TEST_F(FilesystemVerifierActionTest, DISABLED_RunAsRootSimpleTest) {
+  ASSERT_EQ(0, getuid());
+  bool test = DoTest(false, false, VerifierMode::kComputeSourceHash);
+  EXPECT_TRUE(test);
+  if (!test)
+    return;
+  test = DoTest(false, false, VerifierMode::kVerifyTargetHash);
+  EXPECT_TRUE(test);
+}
+
+bool FilesystemVerifierActionTest::DoTest(bool terminate_early,
+                                          bool hash_fail,
+                                          VerifierMode verifier_mode) {
+  string a_loop_file;
+
+  if (!(utils::MakeTempFile("a_loop_file.XXXXXX", &a_loop_file, nullptr))) {
+    ADD_FAILURE();
+    return false;
+  }
+  ScopedPathUnlinker a_loop_file_unlinker(a_loop_file);
+
+  // Make random data for a.
+  const size_t kLoopFileSize = 10 * 1024 * 1024 + 512;
+  brillo::Blob a_loop_data(kLoopFileSize);
+  test_utils::FillWithData(&a_loop_data);
+
+  // Write data to disk
+  if (!(test_utils::WriteFileVector(a_loop_file, a_loop_data))) {
+    ADD_FAILURE();
+    return false;
+  }
+
+  // Attach loop devices to the files
+  string a_dev;
+  test_utils::ScopedLoopbackDeviceBinder a_dev_releaser(a_loop_file, &a_dev);
+  if (!(a_dev_releaser.is_bound())) {
+    ADD_FAILURE();
+    return false;
+  }
+
+  LOG(INFO) << "verifying: "  << a_loop_file << " (" << a_dev << ")";
+
+  bool success = true;
+
+  // Set up the action objects
+  InstallPlan install_plan;
+  install_plan.source_slot = 0;
+  install_plan.target_slot = 1;
+  InstallPlan::Partition part;
+  part.name = "part";
+  if (verifier_mode == VerifierMode::kVerifyTargetHash) {
+    part.target_size = kLoopFileSize - (hash_fail ? 1 : 0);
+    part.target_path = a_dev;
+    fake_boot_control_.SetPartitionDevice(
+        part.name, install_plan.target_slot, a_dev);
+    if (!HashCalculator::RawHashOfData(a_loop_data, &part.target_hash)) {
+      ADD_FAILURE();
+      success = false;
+    }
+  }
+  part.source_size = kLoopFileSize;
+  part.source_path = a_dev;
+  fake_boot_control_.SetPartitionDevice(
+      part.name, install_plan.source_slot, a_dev);
+  if (!HashCalculator::RawHashOfData(a_loop_data, &part.source_hash)) {
+    ADD_FAILURE();
+    success = false;
+  }
+  install_plan.partitions = {part};
+
+  ActionProcessor processor;
+
+  ObjectFeederAction<InstallPlan> feeder_action;
+  FilesystemVerifierAction copier_action(&fake_boot_control_, verifier_mode);
+  ObjectCollectorAction<InstallPlan> collector_action;
+
+  BondActions(&feeder_action, &copier_action);
+  BondActions(&copier_action, &collector_action);
+
+  FilesystemVerifierActionTestDelegate delegate(&copier_action);
+  processor.set_delegate(&delegate);
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&copier_action);
+  processor.EnqueueAction(&collector_action);
+
+  feeder_action.set_obj(install_plan);
+
+  loop_.PostTask(FROM_HERE, base::Bind(&StartProcessorInRunLoop,
+                                       &processor,
+                                       &copier_action,
+                                       terminate_early));
+  loop_.Run();
+
+  if (!terminate_early) {
+    bool is_delegate_ran = delegate.ran();
+    EXPECT_TRUE(is_delegate_ran);
+    success = success && is_delegate_ran;
+  } else {
+    EXPECT_EQ(ErrorCode::kError, delegate.code());
+    return (ErrorCode::kError == delegate.code());
+  }
+  if (hash_fail) {
+    ErrorCode expected_exit_code = ErrorCode::kNewRootfsVerificationError;
+    EXPECT_EQ(expected_exit_code, delegate.code());
+    return (expected_exit_code == delegate.code());
+  }
+  EXPECT_EQ(ErrorCode::kSuccess, delegate.code());
+
+  // Make sure everything in the out_image is there
+  brillo::Blob a_out;
+  if (!utils::ReadFile(a_dev, &a_out)) {
+    ADD_FAILURE();
+    return false;
+  }
+  const bool is_a_file_reading_eq =
+      test_utils::ExpectVectorsEq(a_loop_data, a_out);
+  EXPECT_TRUE(is_a_file_reading_eq);
+  success = success && is_a_file_reading_eq;
+
+  bool is_install_plan_eq = (collector_action.object() == install_plan);
+  EXPECT_TRUE(is_install_plan_eq);
+  success = success && is_install_plan_eq;
+  return success;
+}
+
+class FilesystemVerifierActionTest2Delegate : public ActionProcessorDelegate {
+ public:
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) {
+    if (action->Type() == FilesystemVerifierAction::StaticType()) {
+      ran_ = true;
+      code_ = code;
+    }
+  }
+  bool ran_;
+  ErrorCode code_;
+};
+
+TEST_F(FilesystemVerifierActionTest, MissingInputObjectTest) {
+  ActionProcessor processor;
+  FilesystemVerifierActionTest2Delegate delegate;
+
+  processor.set_delegate(&delegate);
+
+  FilesystemVerifierAction copier_action(&fake_boot_control_,
+                                         VerifierMode::kVerifyTargetHash);
+  ObjectCollectorAction<InstallPlan> collector_action;
+
+  BondActions(&copier_action, &collector_action);
+
+  processor.EnqueueAction(&copier_action);
+  processor.EnqueueAction(&collector_action);
+  processor.StartProcessing();
+  EXPECT_FALSE(processor.IsRunning());
+  EXPECT_TRUE(delegate.ran_);
+  EXPECT_EQ(ErrorCode::kError, delegate.code_);
+}
+
+TEST_F(FilesystemVerifierActionTest, NonExistentDriveTest) {
+  ActionProcessor processor;
+  FilesystemVerifierActionTest2Delegate delegate;
+
+  processor.set_delegate(&delegate);
+
+  ObjectFeederAction<InstallPlan> feeder_action;
+  InstallPlan install_plan(false,
+                           false,
+                           "",
+                           0,
+                           "",
+                           0,
+                           "",
+                           "");
+  InstallPlan::Partition part;
+  part.name = "nope";
+  part.source_path = "/no/such/file";
+  part.target_path = "/no/such/file";
+  install_plan.partitions = {part};
+
+  feeder_action.set_obj(install_plan);
+  FilesystemVerifierAction verifier_action(&fake_boot_control_,
+                                           VerifierMode::kVerifyTargetHash);
+  ObjectCollectorAction<InstallPlan> collector_action;
+
+  BondActions(&verifier_action, &collector_action);
+
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&verifier_action);
+  processor.EnqueueAction(&collector_action);
+  processor.StartProcessing();
+  EXPECT_FALSE(processor.IsRunning());
+  EXPECT_TRUE(delegate.ran_);
+  EXPECT_EQ(ErrorCode::kError, delegate.code_);
+}
+
+TEST_F(FilesystemVerifierActionTest, RunAsRootVerifyHashTest) {
+  ASSERT_EQ(0, getuid());
+  EXPECT_TRUE(DoTest(false, false, VerifierMode::kVerifyTargetHash));
+  EXPECT_TRUE(DoTest(false, false, VerifierMode::kComputeSourceHash));
+}
+
+TEST_F(FilesystemVerifierActionTest, RunAsRootVerifyHashFailTest) {
+  ASSERT_EQ(0, getuid());
+  EXPECT_TRUE(DoTest(false, true, VerifierMode::kVerifyTargetHash));
+}
+
+TEST_F(FilesystemVerifierActionTest, RunAsRootTerminateEarlyTest) {
+  ASSERT_EQ(0, getuid());
+  EXPECT_TRUE(DoTest(true, false, VerifierMode::kVerifyTargetHash));
+  // TerminateEarlyTest may leak some null callbacks from the Stream class.
+  while (loop_.RunOnce(false)) {}
+}
+
+// Disabled as we switched to minor version 3, so this test is obsolete, will be
+// deleted when we delete the corresponding code in PerformAction().
+// Test that the rootfs and kernel size used for hashing in delta payloads for
+// major version 1 is properly read.
+TEST_F(FilesystemVerifierActionTest,
+       DISABLED_RunAsRootDetermineLegacySizeTest) {
+  string img;
+  EXPECT_TRUE(utils::MakeTempFile("img.XXXXXX", &img, nullptr));
+  ScopedPathUnlinker img_unlinker(img);
+  test_utils::CreateExtImageAtPath(img, nullptr);
+  // Extend the "partition" holding the file system from 10MiB to 20MiB.
+  EXPECT_EQ(0, truncate(img.c_str(), 20 * 1024 * 1024));
+
+  InstallPlan install_plan;
+  install_plan.source_slot = 1;
+
+  fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameRoot, install_plan.source_slot, img);
+  fake_boot_control_.SetPartitionDevice(
+      kLegacyPartitionNameKernel, install_plan.source_slot, img);
+  FilesystemVerifierAction action(&fake_boot_control_,
+                                  VerifierMode::kComputeSourceHash);
+
+  ObjectFeederAction<InstallPlan> feeder_action;
+  feeder_action.set_obj(install_plan);
+
+  ObjectCollectorAction<InstallPlan> collector_action;
+
+  BondActions(&feeder_action, &action);
+  BondActions(&action, &collector_action);
+  ActionProcessor processor;
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&action);
+  processor.EnqueueAction(&collector_action);
+
+  loop_.PostTask(FROM_HERE,
+                 base::Bind([&processor]{ processor.StartProcessing(); }));
+  loop_.Run();
+  install_plan = collector_action.object();
+
+  ASSERT_EQ(2, install_plan.partitions.size());
+  // When computing the size of the rootfs on legacy delta updates we use the
+  // size of the filesystem, but when updating the kernel we use the whole
+  // partition.
+  EXPECT_EQ(10 * 1024 * 1024, install_plan.partitions[0].source_size);
+  EXPECT_EQ(kLegacyPartitionNameRoot, install_plan.partitions[0].name);
+  EXPECT_EQ(20 * 1024 * 1024, install_plan.partitions[1].source_size);
+  EXPECT_EQ(kLegacyPartitionNameKernel, install_plan.partitions[1].name);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/install_plan.cc b/payload_consumer/install_plan.cc
new file mode 100644
index 0000000..a2a1b7b
--- /dev/null
+++ b/payload_consumer/install_plan.cc
@@ -0,0 +1,124 @@
+//
+// Copyright (C) 2013 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 "update_engine/payload_consumer/install_plan.h"
+
+#include <base/format_macros.h>
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+InstallPlan::InstallPlan(bool is_resume,
+                         bool is_full_update,
+                         const string& url,
+                         uint64_t payload_size,
+                         const string& payload_hash,
+                         uint64_t metadata_size,
+                         const string& metadata_signature,
+                         const string& public_key_rsa)
+    : is_resume(is_resume),
+      is_full_update(is_full_update),
+      download_url(url),
+      payload_size(payload_size),
+      payload_hash(payload_hash),
+      metadata_size(metadata_size),
+      metadata_signature(metadata_signature),
+      hash_checks_mandatory(false),
+      powerwash_required(false),
+      public_key_rsa(public_key_rsa) {}
+
+
+bool InstallPlan::operator==(const InstallPlan& that) const {
+  return ((is_resume == that.is_resume) &&
+          (is_full_update == that.is_full_update) &&
+          (download_url == that.download_url) &&
+          (payload_size == that.payload_size) &&
+          (payload_hash == that.payload_hash) &&
+          (metadata_size == that.metadata_size) &&
+          (metadata_signature == that.metadata_signature) &&
+          (source_slot == that.source_slot) &&
+          (target_slot == that.target_slot) &&
+          (partitions == that.partitions));
+}
+
+bool InstallPlan::operator!=(const InstallPlan& that) const {
+  return !((*this) == that);
+}
+
+void InstallPlan::Dump() const {
+  string partitions_str;
+  for (const auto& partition : partitions) {
+    partitions_str += base::StringPrintf(
+        ", part: %s (source_size: %" PRIu64 ", target_size %" PRIu64 ")",
+        partition.name.c_str(), partition.source_size, partition.target_size);
+  }
+
+  LOG(INFO) << "InstallPlan: "
+            << (is_resume ? "resume" : "new_update")
+            << ", payload type: " << (is_full_update ? "full" : "delta")
+            << ", source_slot: " << BootControlInterface::SlotName(source_slot)
+            << ", target_slot: " << BootControlInterface::SlotName(target_slot)
+            << ", url: " << download_url
+            << ", payload size: " << payload_size
+            << ", payload hash: " << payload_hash
+            << ", metadata size: " << metadata_size
+            << ", metadata signature: " << metadata_signature
+            << partitions_str
+            << ", hash_checks_mandatory: " << utils::ToString(
+                hash_checks_mandatory)
+            << ", powerwash_required: " << utils::ToString(
+                powerwash_required);
+}
+
+bool InstallPlan::LoadPartitionsFromSlots(BootControlInterface* boot_control) {
+  bool result = true;
+  for (Partition& partition : partitions) {
+    if (source_slot != BootControlInterface::kInvalidSlot) {
+      result = boot_control->GetPartitionDevice(
+          partition.name, source_slot, &partition.source_path) && result;
+    } else {
+      partition.source_path.clear();
+    }
+
+    if (target_slot != BootControlInterface::kInvalidSlot) {
+      result = boot_control->GetPartitionDevice(
+          partition.name, target_slot, &partition.target_path) && result;
+    } else {
+      partition.target_path.clear();
+    }
+  }
+  return result;
+}
+
+bool InstallPlan::Partition::operator==(
+    const InstallPlan::Partition& that) const {
+  return (name == that.name &&
+          source_path == that.source_path &&
+          source_size == that.source_size &&
+          source_hash == that.source_hash &&
+          target_path == that.target_path &&
+          target_size == that.target_size &&
+          target_hash == that.target_hash &&
+          run_postinstall == that.run_postinstall);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/install_plan.h b/payload_consumer/install_plan.h
new file mode 100644
index 0000000..e69462d
--- /dev/null
+++ b/payload_consumer/install_plan.h
@@ -0,0 +1,156 @@
+//
+// Copyright (C) 2011 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_INSTALL_PLAN_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_INSTALL_PLAN_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/common/action.h"
+#include "update_engine/common/boot_control_interface.h"
+
+// InstallPlan is a simple struct that contains relevant info for many
+// parts of the update system about the install that should happen.
+namespace chromeos_update_engine {
+
+struct InstallPlan {
+  InstallPlan(bool is_resume,
+              bool is_full_update,
+              const std::string& url,
+              uint64_t payload_size,
+              const std::string& payload_hash,
+              uint64_t metadata_size,
+              const std::string& metadata_signature,
+              const std::string& public_key_rsa);
+
+  // Default constructor.
+  InstallPlan() = default;
+
+  bool operator==(const InstallPlan& that) const;
+  bool operator!=(const InstallPlan& that) const;
+
+  void Dump() const;
+
+  // Load the |source_path| and |target_path| of all |partitions| based on the
+  // |source_slot| and |target_slot| if available. Returns whether it succeeded
+  // to load all the partitions for the valid slots.
+  bool LoadPartitionsFromSlots(BootControlInterface* boot_control);
+
+  bool is_resume{false};
+  bool is_full_update{false};
+  std::string download_url;  // url to download from
+  std::string version;       // version we are installing.
+
+  uint64_t payload_size{0};              // size of the payload
+  std::string payload_hash;              // SHA256 hash of the payload
+  uint64_t metadata_size{0};             // size of the metadata
+  std::string metadata_signature;        // signature of the  metadata
+
+  // The partition slots used for the update.
+  BootControlInterface::Slot source_slot{BootControlInterface::kInvalidSlot};
+  BootControlInterface::Slot target_slot{BootControlInterface::kInvalidSlot};
+
+  // The vector below is used for partition verification. The flow is:
+  //
+  // 1. FilesystemVerifierAction computes and fills in the source partition
+  // hash based on the guessed source size for delta major version 1 updates.
+  //
+  // 2. DownloadAction verifies the source partition sizes and hashes against
+  // the expected values transmitted in the update manifest. It fills in the
+  // expected target partition sizes and hashes based on the manifest.
+  //
+  // 3. FilesystemVerifierAction computes and verifies the applied partition
+  // sizes and hashes against the expected values in target_partition_hashes.
+  struct Partition {
+    bool operator==(const Partition& that) const;
+
+    // The name of the partition.
+    std::string name;
+
+    std::string source_path;
+    uint64_t source_size{0};
+    brillo::Blob source_hash;
+
+    std::string target_path;
+    uint64_t target_size{0};
+    brillo::Blob target_hash;
+
+    // Whether we should run the postinstall script from this partition.
+    bool run_postinstall{false};
+  };
+  std::vector<Partition> partitions;
+
+  // True if payload hash checks are mandatory based on the system state and
+  // the Omaha response.
+  bool hash_checks_mandatory{false};
+
+  // True if Powerwash is required on reboot after applying the payload.
+  // False otherwise.
+  bool powerwash_required{false};
+
+  // If not blank, a base-64 encoded representation of the PEM-encoded
+  // public key in the response.
+  std::string public_key_rsa;
+};
+
+class InstallPlanAction;
+
+template<>
+class ActionTraits<InstallPlanAction> {
+ public:
+  // Takes the install plan as input
+  typedef InstallPlan InputObjectType;
+  // Passes the install plan as output
+  typedef InstallPlan OutputObjectType;
+};
+
+// Basic action that only receives and sends Install Plans.
+// Can be used to construct an Install Plan to send to any other Action that
+// accept an InstallPlan.
+class InstallPlanAction : public Action<InstallPlanAction> {
+ public:
+  InstallPlanAction() {}
+  explicit InstallPlanAction(const InstallPlan& install_plan):
+    install_plan_(install_plan) {}
+
+  void PerformAction() override {
+    if (HasOutputPipe()) {
+      SetOutputObject(install_plan_);
+    }
+    processor_->ActionComplete(this, ErrorCode::kSuccess);
+  }
+
+  InstallPlan* install_plan() { return &install_plan_; }
+
+  static std::string StaticType() { return "InstallPlanAction"; }
+  std::string Type() const override { return StaticType(); }
+
+  typedef ActionTraits<InstallPlanAction>::InputObjectType InputObjectType;
+  typedef ActionTraits<InstallPlanAction>::OutputObjectType OutputObjectType;
+
+ private:
+  InstallPlan install_plan_;
+
+  DISALLOW_COPY_AND_ASSIGN(InstallPlanAction);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_INSTALL_PLAN_H_
diff --git a/payload_consumer/mock_download_action.h b/payload_consumer/mock_download_action.h
new file mode 100644
index 0000000..3abb809
--- /dev/null
+++ b/payload_consumer/mock_download_action.h
@@ -0,0 +1,41 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_MOCK_DOWNLOAD_ACTION_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_MOCK_DOWNLOAD_ACTION_H_
+
+#include <stdint.h>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/common/error_code.h"
+#include "update_engine/payload_consumer/download_action.h"
+
+namespace chromeos_update_engine {
+
+class MockDownloadActionDelegate : public DownloadActionDelegate {
+ public:
+  MOCK_METHOD3(BytesReceived,
+               void(uint64_t bytes_progressed,
+                    uint64_t bytes_received,
+                    uint64_t total));
+  MOCK_METHOD1(ShouldCancel, bool(ErrorCode* cancel_reason));
+  MOCK_METHOD0(DownloadComplete, void());
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_MOCK_DOWNLOAD_ACTION_H_
diff --git a/payload_consumer/mtd_file_descriptor.cc b/payload_consumer/mtd_file_descriptor.cc
new file mode 100644
index 0000000..da8fd58
--- /dev/null
+++ b/payload_consumer/mtd_file_descriptor.cc
@@ -0,0 +1,265 @@
+//
+// Copyright (C) 2014 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 "update_engine/payload_consumer/mtd_file_descriptor.h"
+
+#include <fcntl.h>
+#include <mtd/ubi-user.h>
+#include <string>
+#include <sys/ioctl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <vector>
+
+#include <base/files/file_path.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace {
+
+static const char kSysfsClassUbi[] = "/sys/class/ubi/";
+static const char kUsableEbSize[] = "/usable_eb_size";
+static const char kReservedEbs[] = "/reserved_ebs";
+
+using chromeos_update_engine::UbiVolumeInfo;
+using chromeos_update_engine::utils::ReadFile;
+
+// Return a UbiVolumeInfo pointer if |path| is a UBI volume. Otherwise, return
+// a null unique pointer.
+std::unique_ptr<UbiVolumeInfo> GetUbiVolumeInfo(const string& path) {
+  base::FilePath device_node(path);
+  base::FilePath ubi_name(device_node.BaseName());
+
+  string sysfs_node(kSysfsClassUbi);
+  sysfs_node.append(ubi_name.MaybeAsASCII());
+
+  std::unique_ptr<UbiVolumeInfo> ret;
+
+  // Obtain volume info from sysfs.
+  string s_reserved_ebs;
+  if (!ReadFile(sysfs_node + kReservedEbs, &s_reserved_ebs)) {
+    LOG(ERROR) << "Cannot read " << sysfs_node + kReservedEbs;
+    return ret;
+  }
+  string s_eb_size;
+  if (!ReadFile(sysfs_node + kUsableEbSize, &s_eb_size)) {
+    LOG(ERROR) << "Cannot read " << sysfs_node + kUsableEbSize;
+    return ret;
+  }
+
+  base::TrimWhitespaceASCII(s_reserved_ebs,
+                            base::TRIM_TRAILING,
+                            &s_reserved_ebs);
+  base::TrimWhitespaceASCII(s_eb_size, base::TRIM_TRAILING, &s_eb_size);
+
+  uint64_t reserved_ebs, eb_size;
+  if (!base::StringToUint64(s_reserved_ebs, &reserved_ebs)) {
+    LOG(ERROR) << "Cannot parse reserved_ebs: " << s_reserved_ebs;
+    return ret;
+  }
+  if (!base::StringToUint64(s_eb_size, &eb_size)) {
+    LOG(ERROR) << "Cannot parse usable_eb_size: " << s_eb_size;
+    return ret;
+  }
+
+  ret.reset(new UbiVolumeInfo);
+  ret->reserved_ebs = reserved_ebs;
+  ret->eraseblock_size = eb_size;
+  return ret;
+}
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+MtdFileDescriptor::MtdFileDescriptor()
+    : read_ctx_(nullptr, &mtd_read_close),
+      write_ctx_(nullptr, &mtd_write_close) {}
+
+bool MtdFileDescriptor::IsMtd(const char* path) {
+  uint64_t size;
+  return mtd_node_info(path, &size, nullptr, nullptr) == 0;
+}
+
+bool MtdFileDescriptor::Open(const char* path, int flags, mode_t mode) {
+  // This File Descriptor does not support read and write.
+  TEST_AND_RETURN_FALSE((flags & O_ACCMODE) != O_RDWR);
+  // But we need to open the underlying file descriptor in O_RDWR mode because
+  // during write, we need to read back to verify the write actually sticks or
+  // we have to skip the block. That job is done by mtdutils library.
+  if ((flags & O_ACCMODE) == O_WRONLY) {
+    flags &= ~O_ACCMODE;
+    flags |= O_RDWR;
+  }
+  TEST_AND_RETURN_FALSE(
+      EintrSafeFileDescriptor::Open(path, flags | O_CLOEXEC, mode));
+
+  if ((flags & O_ACCMODE) == O_RDWR) {
+    write_ctx_.reset(mtd_write_descriptor(fd_, path));
+    nr_written_ = 0;
+  } else {
+    read_ctx_.reset(mtd_read_descriptor(fd_, path));
+  }
+
+  if (!read_ctx_ && !write_ctx_) {
+    Close();
+    return false;
+  }
+
+  return true;
+}
+
+bool MtdFileDescriptor::Open(const char* path, int flags) {
+  mode_t cur = umask(022);
+  umask(cur);
+  return Open(path, flags, 0777 & ~cur);
+}
+
+ssize_t MtdFileDescriptor::Read(void* buf, size_t count) {
+  CHECK(read_ctx_);
+  return mtd_read_data(read_ctx_.get(), static_cast<char*>(buf), count);
+}
+
+ssize_t MtdFileDescriptor::Write(const void* buf, size_t count) {
+  CHECK(write_ctx_);
+  ssize_t result = mtd_write_data(write_ctx_.get(),
+                                  static_cast<const char*>(buf),
+                                  count);
+  if (result > 0) {
+    nr_written_ += result;
+  }
+  return result;
+}
+
+off64_t MtdFileDescriptor::Seek(off64_t offset, int whence) {
+  if (write_ctx_) {
+    // Ignore seek in write mode.
+    return nr_written_;
+  }
+  return EintrSafeFileDescriptor::Seek(offset, whence);
+}
+
+bool MtdFileDescriptor::Close() {
+  read_ctx_.reset();
+  write_ctx_.reset();
+  return EintrSafeFileDescriptor::Close();
+}
+
+bool UbiFileDescriptor::IsUbi(const char* path) {
+  base::FilePath device_node(path);
+  base::FilePath ubi_name(device_node.BaseName());
+  TEST_AND_RETURN_FALSE(
+      base::StartsWithASCII(ubi_name.MaybeAsASCII(), "ubi", true));
+
+  return static_cast<bool>(GetUbiVolumeInfo(path));
+}
+
+bool UbiFileDescriptor::Open(const char* path, int flags, mode_t mode) {
+  std::unique_ptr<UbiVolumeInfo> info = GetUbiVolumeInfo(path);
+  if (!info) {
+    return false;
+  }
+
+  // This File Descriptor does not support read and write.
+  TEST_AND_RETURN_FALSE((flags & O_ACCMODE) != O_RDWR);
+  TEST_AND_RETURN_FALSE(
+      EintrSafeFileDescriptor::Open(path, flags | O_CLOEXEC, mode));
+
+  usable_eb_blocks_ = info->reserved_ebs;
+  eraseblock_size_ = info->eraseblock_size;
+  volume_size_ = usable_eb_blocks_ * eraseblock_size_;
+
+  if ((flags & O_ACCMODE) == O_WRONLY) {
+    // It's best to use volume update ioctl so that UBI layer will mark the
+    // volume as being updated, and only clear that mark if the update is
+    // successful. We will need to pad to the whole volume size at close.
+    uint64_t vsize = volume_size_;
+    if (ioctl(fd_, UBI_IOCVOLUP, &vsize) != 0) {
+      PLOG(ERROR) << "Cannot issue volume update ioctl";
+      EintrSafeFileDescriptor::Close();
+      return false;
+    }
+    mode_ = kWriteOnly;
+    nr_written_ = 0;
+  } else {
+    mode_ = kReadOnly;
+  }
+
+  return true;
+}
+
+bool UbiFileDescriptor::Open(const char* path, int flags) {
+  mode_t cur = umask(022);
+  umask(cur);
+  return Open(path, flags, 0777 & ~cur);
+}
+
+ssize_t UbiFileDescriptor::Read(void* buf, size_t count) {
+  CHECK(mode_ == kReadOnly);
+  return EintrSafeFileDescriptor::Read(buf, count);
+}
+
+ssize_t UbiFileDescriptor::Write(const void* buf, size_t count) {
+  CHECK(mode_ == kWriteOnly);
+  ssize_t nr_chunk = EintrSafeFileDescriptor::Write(buf, count);
+  if (nr_chunk >= 0) {
+    nr_written_ += nr_chunk;
+  }
+  return nr_chunk;
+}
+
+off64_t UbiFileDescriptor::Seek(off64_t offset, int whence) {
+  if (mode_ == kWriteOnly) {
+    // Ignore seek in write mode.
+    return nr_written_;
+  }
+  return EintrSafeFileDescriptor::Seek(offset, whence);
+}
+
+bool UbiFileDescriptor::Close() {
+  bool pad_ok = true;
+  if (IsOpen() && mode_ == kWriteOnly) {
+    char buf[1024];
+    memset(buf, 0xFF, sizeof(buf));
+    while (nr_written_ < volume_size_) {
+      // We have written less than the whole volume. In order for us to clear
+      // the update marker, we need to fill the rest. It is recommended to fill
+      // UBI writes with 0xFF.
+      uint64_t to_write = volume_size_ - nr_written_;
+      if (to_write > sizeof(buf)) {
+        to_write = sizeof(buf);
+      }
+      ssize_t nr_chunk = EintrSafeFileDescriptor::Write(buf, to_write);
+      if (nr_chunk < 0) {
+        LOG(ERROR) << "Cannot 0xFF-pad before closing.";
+        // There is an error, but we can't really do any meaningful thing here.
+        pad_ok = false;
+        break;
+      }
+      nr_written_ += nr_chunk;
+    }
+  }
+  return EintrSafeFileDescriptor::Close() && pad_ok;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/mtd_file_descriptor.h b/payload_consumer/mtd_file_descriptor.h
new file mode 100644
index 0000000..9ac1ec1
--- /dev/null
+++ b/payload_consumer/mtd_file_descriptor.h
@@ -0,0 +1,102 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_MTD_FILE_DESCRIPTOR_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_MTD_FILE_DESCRIPTOR_H_
+
+// This module defines file descriptors that deal with NAND media. We are
+// concerned with raw NAND access (as MTD device), and through UBI layer.
+
+#include <mtdutils.h>
+
+#include "update_engine/payload_consumer/file_descriptor.h"
+
+namespace chromeos_update_engine {
+
+// A class defining the file descriptor API for raw MTD device. This file
+// descriptor supports either random read, or sequential write but not both at
+// once.
+class MtdFileDescriptor : public EintrSafeFileDescriptor {
+ public:
+  MtdFileDescriptor();
+
+  static bool IsMtd(const char* path);
+
+  bool Open(const char* path, int flags, mode_t mode) override;
+  bool Open(const char* path, int flags) override;
+  ssize_t Read(void* buf, size_t count) override;
+  ssize_t Write(const void* buf, size_t count) override;
+  off64_t Seek(off64_t offset, int whence) override;
+  bool BlkIoctl(int request,
+                uint64_t start,
+                uint64_t length,
+                int* result) override {
+    return false;
+  }
+  bool Close() override;
+
+ private:
+  std::unique_ptr<MtdReadContext, decltype(&mtd_read_close)> read_ctx_;
+  std::unique_ptr<MtdWriteContext, decltype(&mtd_write_close)> write_ctx_;
+  uint64_t nr_written_;
+};
+
+struct UbiVolumeInfo {
+  // Number of eraseblocks.
+  uint64_t reserved_ebs;
+  // Size of each eraseblock.
+  uint64_t eraseblock_size;
+};
+
+// A file descriptor to update a UBI volume, similar to MtdFileDescriptor.
+// Once the file descriptor is opened for write, the volume is marked as being
+// updated. The volume will not be usable until an update is completed. See
+// UBI_IOCVOLUP ioctl operation.
+class UbiFileDescriptor : public EintrSafeFileDescriptor {
+ public:
+  // Perform some queries about |path| to see if it is a UBI volume.
+  static bool IsUbi(const char* path);
+
+  bool Open(const char* path, int flags, mode_t mode) override;
+  bool Open(const char* path, int flags) override;
+  ssize_t Read(void* buf, size_t count) override;
+  ssize_t Write(const void* buf, size_t count) override;
+  off64_t Seek(off64_t offset, int whence) override;
+  bool BlkIoctl(int request,
+                uint64_t start,
+                uint64_t length,
+                int* result) override {
+    return false;
+  }
+  bool Close() override;
+
+ private:
+  enum Mode {
+    kReadOnly,
+    kWriteOnly
+  };
+
+  uint64_t usable_eb_blocks_;
+  uint64_t eraseblock_size_;
+  uint64_t volume_size_;
+  uint64_t nr_written_;
+
+  Mode mode_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_MTD_FILE_DESCRIPTOR_H_
diff --git a/payload_consumer/payload_constants.cc b/payload_consumer/payload_constants.cc
new file mode 100644
index 0000000..72abf8c
--- /dev/null
+++ b/payload_consumer/payload_constants.cc
@@ -0,0 +1,59 @@
+//
+// Copyright (C) 2014 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 "update_engine/payload_consumer/payload_constants.h"
+
+namespace chromeos_update_engine {
+
+const uint64_t kChromeOSMajorPayloadVersion = 1;
+const uint64_t kBrilloMajorPayloadVersion = 2;
+
+const uint32_t kFullPayloadMinorVersion = 0;
+const uint32_t kInPlaceMinorPayloadVersion = 1;
+const uint32_t kSourceMinorPayloadVersion = 2;
+const uint32_t kOpSrcHashMinorPayloadVersion = 3;
+
+const char kLegacyPartitionNameKernel[] = "boot";
+const char kLegacyPartitionNameRoot[] = "system";
+
+const char kDeltaMagic[4] = {'C', 'r', 'A', 'U'};
+const char kBspatchPath[] = "bspatch";
+
+const char* InstallOperationTypeName(InstallOperation_Type op_type) {
+  switch (op_type) {
+    case InstallOperation::BSDIFF:
+      return "BSDIFF";
+    case InstallOperation::MOVE:
+      return "MOVE";
+    case InstallOperation::REPLACE:
+      return "REPLACE";
+    case InstallOperation::REPLACE_BZ:
+      return "REPLACE_BZ";
+    case InstallOperation::SOURCE_COPY:
+      return "SOURCE_COPY";
+    case InstallOperation::SOURCE_BSDIFF:
+      return "SOURCE_BSDIFF";
+    case InstallOperation::ZERO:
+      return "ZERO";
+    case InstallOperation::DISCARD:
+      return "DISCARD";
+    case InstallOperation::REPLACE_XZ:
+      return "REPLACE_XZ";
+  }
+  return "<unknown_op>";
+}
+
+};  // namespace chromeos_update_engine
diff --git a/payload_consumer/payload_constants.h b/payload_consumer/payload_constants.h
new file mode 100644
index 0000000..c3cd363
--- /dev/null
+++ b/payload_consumer/payload_constants.h
@@ -0,0 +1,65 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_CONSTANTS_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_CONSTANTS_H_
+
+#include <stdint.h>
+
+#include <limits>
+
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+// The major version used by Chrome OS.
+extern const uint64_t kChromeOSMajorPayloadVersion;
+
+// The major version used by Brillo.
+extern const uint64_t kBrilloMajorPayloadVersion;
+
+// The minor version used for all full payloads.
+extern const uint32_t kFullPayloadMinorVersion;
+
+// The minor version used by the in-place delta generator algorithm.
+extern const uint32_t kInPlaceMinorPayloadVersion;
+
+// The minor version used by the A to B delta generator algorithm.
+extern const uint32_t kSourceMinorPayloadVersion;
+
+// The minor version that allows per-operation source hash.
+extern const uint32_t kOpSrcHashMinorPayloadVersion;
+
+
+// The kernel and rootfs partition names used by the BootControlInterface when
+// handling update payloads with a major version 1. The names of the updated
+// partitions are include in the payload itself for major version 2.
+extern const char kLegacyPartitionNameKernel[];
+extern const char kLegacyPartitionNameRoot[];
+
+extern const char kBspatchPath[];
+extern const char kDeltaMagic[4];
+
+// A block number denoting a hole on a sparse file. Used on Extents to refer to
+// section of blocks not present on disk on a sparse file.
+const uint64_t kSparseHole = std::numeric_limits<uint64_t>::max();
+
+// Return the name of the operation type.
+const char* InstallOperationTypeName(InstallOperation_Type op_type);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_CONSTANTS_H_
diff --git a/payload_consumer/payload_verifier.cc b/payload_consumer/payload_verifier.cc
new file mode 100644
index 0000000..ab5238c
--- /dev/null
+++ b/payload_consumer/payload_verifier.cc
@@ -0,0 +1,183 @@
+//
+// Copyright (C) 2014 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 "update_engine/payload_consumer/payload_verifier.h"
+
+#include <base/logging.h>
+#include <openssl/pem.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// The following is a standard PKCS1-v1_5 padding for SHA256 signatures, as
+// defined in RFC3447. It is prepended to the actual signature (32 bytes) to
+// form a sequence of 256 bytes (2048 bits) that is amenable to RSA signing. The
+// padded hash will look as follows:
+//
+//    0x00 0x01 0xff ... 0xff 0x00  ASN1HEADER  SHA256HASH
+//   |--------------205-----------||----19----||----32----|
+//
+// where ASN1HEADER is the ASN.1 description of the signed data. The complete 51
+// bytes of actual data (i.e. the ASN.1 header complete with the hash) are
+// packed as follows:
+//
+//  SEQUENCE(2+49) {
+//   SEQUENCE(2+13) {
+//    OBJECT(2+9) id-sha256
+//    NULL(2+0)
+//   }
+//   OCTET STRING(2+32) <actual signature bytes...>
+//  }
+const uint8_t kRSA2048SHA256Padding[] = {
+  // PKCS1-v1_5 padding
+  0x00, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+  0xff, 0xff, 0xff, 0xff, 0x00,
+  // ASN.1 header
+  0x30, 0x31, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86,
+  0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05,
+  0x00, 0x04, 0x20,
+};
+
+}  // namespace
+
+bool PayloadVerifier::VerifySignature(const brillo::Blob& signature_blob,
+                                      const string& public_key_path,
+                                      const brillo::Blob& hash_data) {
+  TEST_AND_RETURN_FALSE(!public_key_path.empty());
+
+  Signatures signatures;
+  LOG(INFO) << "signature blob size = " <<  signature_blob.size();
+  TEST_AND_RETURN_FALSE(signatures.ParseFromArray(signature_blob.data(),
+                                                  signature_blob.size()));
+
+  if (!signatures.signatures_size()) {
+    LOG(ERROR) << "No signatures stored in the blob.";
+    return false;
+  }
+
+  std::vector<brillo::Blob> tested_hashes;
+  // Tries every signature in the signature blob.
+  for (int i = 0; i < signatures.signatures_size(); i++) {
+    const Signatures_Signature& signature = signatures.signatures(i);
+    brillo::Blob sig_data(signature.data().begin(), signature.data().end());
+    brillo::Blob sig_hash_data;
+    if (!GetRawHashFromSignature(sig_data, public_key_path, &sig_hash_data))
+      continue;
+
+    if (hash_data == sig_hash_data) {
+      LOG(INFO) << "Verified correct signature " << i + 1 << " out of "
+                << signatures.signatures_size() << " signatures.";
+      return true;
+    }
+    tested_hashes.push_back(sig_hash_data);
+  }
+  LOG(ERROR) << "None of the " << signatures.signatures_size()
+             << " signatures is correct. Expected:";
+  utils::HexDumpVector(hash_data);
+  LOG(ERROR) << "But found decrypted hashes:";
+  for (const auto& sig_hash_data : tested_hashes) {
+    utils::HexDumpVector(sig_hash_data);
+  }
+  return false;
+}
+
+
+bool PayloadVerifier::GetRawHashFromSignature(
+    const brillo::Blob& sig_data,
+    const string& public_key_path,
+    brillo::Blob* out_hash_data) {
+  TEST_AND_RETURN_FALSE(!public_key_path.empty());
+
+  // The code below executes the equivalent of:
+  //
+  // openssl rsautl -verify -pubin -inkey |public_key_path|
+  //   -in |sig_data| -out |out_hash_data|
+
+  // Loads the public key.
+  FILE* fpubkey = fopen(public_key_path.c_str(), "rb");
+  if (!fpubkey) {
+    LOG(ERROR) << "Unable to open public key file: " << public_key_path;
+    return false;
+  }
+
+  char dummy_password[] = { ' ', 0 };  // Ensure no password is read from stdin.
+  RSA* rsa = PEM_read_RSA_PUBKEY(fpubkey, nullptr, nullptr, dummy_password);
+  fclose(fpubkey);
+  TEST_AND_RETURN_FALSE(rsa != nullptr);
+  unsigned int keysize = RSA_size(rsa);
+  if (sig_data.size() > 2 * keysize) {
+    LOG(ERROR) << "Signature size is too big for public key size.";
+    RSA_free(rsa);
+    return false;
+  }
+
+  // Decrypts the signature.
+  brillo::Blob hash_data(keysize);
+  int decrypt_size = RSA_public_decrypt(sig_data.size(),
+                                        sig_data.data(),
+                                        hash_data.data(),
+                                        rsa,
+                                        RSA_NO_PADDING);
+  RSA_free(rsa);
+  TEST_AND_RETURN_FALSE(decrypt_size > 0 &&
+                        decrypt_size <= static_cast<int>(hash_data.size()));
+  hash_data.resize(decrypt_size);
+  out_hash_data->swap(hash_data);
+  return true;
+}
+
+bool PayloadVerifier::PadRSA2048SHA256Hash(brillo::Blob* hash) {
+  TEST_AND_RETURN_FALSE(hash->size() == 32);
+  hash->insert(hash->begin(),
+               reinterpret_cast<const char*>(kRSA2048SHA256Padding),
+               reinterpret_cast<const char*>(kRSA2048SHA256Padding +
+                                             sizeof(kRSA2048SHA256Padding)));
+  TEST_AND_RETURN_FALSE(hash->size() == 256);
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/payload_verifier.h b/payload_consumer/payload_verifier.h
new file mode 100644
index 0000000..22ced40
--- /dev/null
+++ b/payload_consumer/payload_verifier.h
@@ -0,0 +1,65 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_VERIFIER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_VERIFIER_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/update_metadata.pb.h"
+
+// This class encapsulates methods used for payload signature verification.
+// See payload_generator/payload_signer.h for payload signing.
+
+namespace chromeos_update_engine {
+
+class PayloadVerifier {
+ public:
+  // Interprets |signature_blob| as a protocol buffer containing the Signatures
+  // message and decrypts each signature data using the |public_key_path|.
+  // Returns whether *any* of the decrypted hashes matches the |hash_data|.
+  // In case of any error parsing the signatures or the public key, returns
+  // false.
+  static bool VerifySignature(const brillo::Blob& signature_blob,
+                              const std::string& public_key_path,
+                              const brillo::Blob& hash_data);
+
+  // Decrypts sig_data with the given public_key_path and populates
+  // out_hash_data with the decoded raw hash. Returns true if successful,
+  // false otherwise.
+  static bool GetRawHashFromSignature(const brillo::Blob& sig_data,
+                                      const std::string& public_key_path,
+                                      brillo::Blob* out_hash_data);
+
+  // Pads a SHA256 hash so that it may be encrypted/signed with RSA2048
+  // using the PKCS#1 v1.5 scheme.
+  // hash should be a pointer to vector of exactly 256 bits. The vector
+  // will be modified in place and will result in having a length of
+  // 2048 bits. Returns true on success, false otherwise.
+  static bool PadRSA2048SHA256Hash(brillo::Blob* hash);
+
+ private:
+  // This should never be constructed
+  DISALLOW_IMPLICIT_CONSTRUCTORS(PayloadVerifier);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_PAYLOAD_VERIFIER_H_
diff --git a/payload_consumer/postinstall_runner_action.cc b/payload_consumer/postinstall_runner_action.cc
new file mode 100644
index 0000000..84ca398
--- /dev/null
+++ b/payload_consumer/postinstall_runner_action.cc
@@ -0,0 +1,187 @@
+//
+// Copyright (C) 2011 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 "update_engine/payload_consumer/postinstall_runner_action.h"
+
+#include <stdlib.h>
+#include <sys/mount.h>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+
+#include "update_engine/common/action_processor.h"
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+
+namespace chromeos_update_engine {
+
+using std::string;
+using std::vector;
+
+namespace {
+// The absolute path to the post install command.
+const char kPostinstallScript[] = "/postinst";
+
+// Path to the binary file used by kPostinstallScript. Used to get and log the
+// file format of the binary to debug issues when the ELF format on the update
+// doesn't match the one on the current system. This path is not executed.
+const char kDebugPostinstallBinaryPath[] = "/usr/bin/cros_installer";
+}
+
+void PostinstallRunnerAction::PerformAction() {
+  CHECK(HasInputObject());
+  install_plan_ = GetInputObject();
+
+  if (install_plan_.powerwash_required) {
+    if (utils::CreatePowerwashMarkerFile(powerwash_marker_file_)) {
+      powerwash_marker_created_ = true;
+    } else {
+      return CompletePostinstall(ErrorCode::kPostinstallPowerwashError);
+    }
+  }
+
+  PerformPartitionPostinstall();
+}
+
+void PostinstallRunnerAction::PerformPartitionPostinstall() {
+  // Skip all the partitions that don't have a post-install step.
+  while (current_partition_ < install_plan_.partitions.size() &&
+         !install_plan_.partitions[current_partition_].run_postinstall) {
+    VLOG(1) << "Skipping post-install on partition "
+            << install_plan_.partitions[current_partition_].name;
+    current_partition_++;
+  }
+  if (current_partition_ == install_plan_.partitions.size())
+    return CompletePostinstall(ErrorCode::kSuccess);
+
+  const InstallPlan::Partition& partition =
+      install_plan_.partitions[current_partition_];
+
+  const string mountable_device =
+      utils::MakePartitionNameForMount(partition.target_path);
+  if (mountable_device.empty()) {
+    LOG(ERROR) << "Cannot make mountable device from " << partition.target_path;
+    return CompletePostinstall(ErrorCode::kPostinstallRunnerError);
+  }
+
+  // Perform post-install for the current_partition_ partition. At this point we
+  // need to call CompletePartitionPostinstall to complete the operation and
+  // cleanup.
+  TEST_AND_RETURN(
+      utils::MakeTempDirectory("au_postint_mount.XXXXXX", &temp_rootfs_dir_));
+
+  if (!utils::MountFilesystem(mountable_device, temp_rootfs_dir_, MS_RDONLY)) {
+    return CompletePartitionPostinstall(
+        1, "Error mounting the device " + mountable_device);
+  }
+
+  LOG(INFO) << "Performing postinst (" << kPostinstallScript
+            << ") installed on device " << partition.target_path
+            << " and mountable device " << mountable_device;
+
+  // Logs the file format of the postinstall script we are about to run. This
+  // will help debug when the postinstall script doesn't match the architecture
+  // of our build.
+  LOG(INFO) << "Format file for new " <<  kPostinstallScript << " is: "
+            << utils::GetFileFormat(temp_rootfs_dir_ + kPostinstallScript);
+  LOG(INFO) << "Format file for new " <<  kDebugPostinstallBinaryPath << " is: "
+            << utils::GetFileFormat(
+                temp_rootfs_dir_ + kDebugPostinstallBinaryPath);
+
+  // Runs the postinstall script asynchronously to free up the main loop while
+  // it's running.
+  vector<string> command;
+  if (!install_plan_.download_url.empty()) {
+    command.push_back(temp_rootfs_dir_ + kPostinstallScript);
+  } else {
+    // TODO(sosa): crbug.com/366207.
+    // If we're doing a rollback, just run our own postinstall.
+    command.push_back(kPostinstallScript);
+  }
+  command.push_back(partition.target_path);
+  if (!Subprocess::Get().Exec(
+          command,
+          base::Bind(
+              &PostinstallRunnerAction::CompletePartitionPostinstall,
+              base::Unretained(this)))) {
+    CompletePartitionPostinstall(1, "Postinstall didn't launch");
+  }
+}
+
+void PostinstallRunnerAction::CompletePartitionPostinstall(
+    int return_code,
+    const string& output) {
+  utils::UnmountFilesystem(temp_rootfs_dir_);
+  if (!base::DeleteFile(base::FilePath(temp_rootfs_dir_), false)) {
+    PLOG(WARNING) << "Not removing mountpoint " << temp_rootfs_dir_;
+  }
+  temp_rootfs_dir_.clear();
+
+  if (return_code != 0) {
+    LOG(ERROR) << "Postinst command failed with code: " << return_code;
+    ErrorCode error_code = ErrorCode::kPostinstallRunnerError;
+
+    if (return_code == 3) {
+      // This special return code means that we tried to update firmware,
+      // but couldn't because we booted from FW B, and we need to reboot
+      // to get back to FW A.
+      error_code = ErrorCode::kPostinstallBootedFromFirmwareB;
+    }
+
+    if (return_code == 4) {
+      // This special return code means that we tried to update firmware,
+      // but couldn't because we booted from FW B, and we need to reboot
+      // to get back to FW A.
+      error_code = ErrorCode::kPostinstallFirmwareRONotUpdatable;
+    }
+    return CompletePostinstall(error_code);
+  }
+  current_partition_++;
+  PerformPartitionPostinstall();
+}
+
+void PostinstallRunnerAction::CompletePostinstall(ErrorCode error_code) {
+  // We only attempt to mark the new slot as active if all the postinstall
+  // steps succeeded.
+  if (error_code == ErrorCode::kSuccess &&
+      !boot_control_->SetActiveBootSlot(install_plan_.target_slot)) {
+    error_code = ErrorCode::kPostinstallRunnerError;
+  }
+
+  ScopedActionCompleter completer(processor_, this);
+
+  if (error_code != ErrorCode::kSuccess) {
+    LOG(ERROR) << "Postinstall action failed.";
+
+    // Undo any changes done to trigger Powerwash using clobber-state.
+    if (powerwash_marker_created_)
+      utils::DeletePowerwashMarkerFile(powerwash_marker_file_);
+
+    return;
+  }
+
+  LOG(INFO) << "All post-install commands succeeded";
+  if (HasOutputPipe()) {
+    SetOutputObject(install_plan_);
+  }
+
+  completer.set_code(ErrorCode::kSuccess);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/postinstall_runner_action.h b/payload_consumer/postinstall_runner_action.h
new file mode 100644
index 0000000..ab267b8
--- /dev/null
+++ b/payload_consumer/postinstall_runner_action.h
@@ -0,0 +1,88 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_POSTINSTALL_RUNNER_ACTION_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_POSTINSTALL_RUNNER_ACTION_H_
+
+#include <string>
+
+#include "update_engine/common/action.h"
+#include "update_engine/payload_consumer/install_plan.h"
+
+// The Postinstall Runner Action is responsible for running the postinstall
+// script of a successfully downloaded update.
+
+namespace chromeos_update_engine {
+
+class BootControlInterface;
+
+class PostinstallRunnerAction : public InstallPlanAction {
+ public:
+  explicit PostinstallRunnerAction(BootControlInterface* boot_control)
+      : PostinstallRunnerAction(boot_control, nullptr) {}
+
+  void PerformAction();
+
+  // Note that there's no support for terminating this action currently.
+  void TerminateProcessing() { CHECK(false); }
+
+  // Debugging/logging
+  static std::string StaticType() { return "PostinstallRunnerAction"; }
+  std::string Type() const { return StaticType(); }
+
+ private:
+  friend class PostinstallRunnerActionTest;
+
+  // Special constructor used for testing purposes.
+  PostinstallRunnerAction(BootControlInterface* boot_control,
+                          const char* powerwash_marker_file)
+      : boot_control_(boot_control),
+        powerwash_marker_file_(powerwash_marker_file) {}
+
+  void PerformPartitionPostinstall();
+
+  // Subprocess::Exec callback.
+  void CompletePartitionPostinstall(int return_code,
+                                    const std::string& output);
+
+  // Complete the Action with the passed |error_code| and mark the new slot as
+  // ready. Called when the post-install script was run for all the partitions.
+  void CompletePostinstall(ErrorCode error_code);
+
+  InstallPlan install_plan_;
+  std::string temp_rootfs_dir_;
+
+  // The partition being processed on the list of partitions specified in the
+  // InstallPlan.
+  size_t current_partition_{0};
+
+  // The BootControlInerface used to mark the new slot as ready.
+  BootControlInterface* boot_control_;
+
+  // True if Powerwash Marker was created before invoking post-install script.
+  // False otherwise. Used for cleaning up if post-install fails.
+  bool powerwash_marker_created_{false};
+
+  // Non-null value will cause post-install to override the default marker
+  // file name; used for testing.
+  const char* powerwash_marker_file_;
+
+  DISALLOW_COPY_AND_ASSIGN(PostinstallRunnerAction);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_POSTINSTALL_RUNNER_ACTION_H_
diff --git a/payload_consumer/postinstall_runner_action_unittest.cc b/payload_consumer/postinstall_runner_action_unittest.cc
new file mode 100644
index 0000000..beed4f1
--- /dev/null
+++ b/payload_consumer/postinstall_runner_action_unittest.cc
@@ -0,0 +1,260 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_consumer/postinstall_runner_action.h"
+
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/files/file_util.h>
+#include <base/message_loop/message_loop.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/message_loops/base_message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using brillo::MessageLoop;
+using chromeos_update_engine::test_utils::System;
+using chromeos_update_engine::test_utils::WriteFileString;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class PostinstallRunnerActionTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    async_signal_handler_.Init();
+    subprocess_.Init(&async_signal_handler_);
+  }
+
+  // DoTest with various combinations of do_losetup, err_code and
+  // powerwash_required.
+  void DoTest(bool do_losetup, int err_code, bool powerwash_required);
+
+ protected:
+  static const char* kImageMountPointTemplate;
+
+  base::MessageLoopForIO base_loop_;
+  brillo::BaseMessageLoop loop_{&base_loop_};
+  brillo::AsynchronousSignalHandler async_signal_handler_;
+  Subprocess subprocess_;
+  FakeBootControl fake_boot_control_;
+};
+
+class PostinstActionProcessorDelegate : public ActionProcessorDelegate {
+ public:
+  PostinstActionProcessorDelegate()
+      : code_(ErrorCode::kError),
+        code_set_(false) {}
+  void ProcessingDone(const ActionProcessor* processor,
+                      ErrorCode code) {
+    MessageLoop::current()->BreakLoop();
+  }
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) {
+    if (action->Type() == PostinstallRunnerAction::StaticType()) {
+      code_ = code;
+      code_set_ = true;
+    }
+  }
+  ErrorCode code_;
+  bool code_set_;
+};
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootSimpleTest) {
+  DoTest(true, 0, false);
+}
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootPowerwashRequiredTest) {
+  DoTest(true, 0, true);
+}
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootCantMountTest) {
+  DoTest(false, 0, true);
+}
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootErrScriptTest) {
+  DoTest(true, 1, false);
+}
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootFirmwareBErrScriptTest) {
+  DoTest(true, 3, false);
+}
+
+TEST_F(PostinstallRunnerActionTest, RunAsRootFirmwareROErrScriptTest) {
+  DoTest(true, 4, false);
+}
+
+const char* PostinstallRunnerActionTest::kImageMountPointTemplate =
+    "au_destination-XXXXXX";
+
+void PostinstallRunnerActionTest::DoTest(
+    bool do_losetup,
+    int err_code,
+    bool powerwash_required) {
+  ASSERT_EQ(0, getuid()) << "Run me as root. Ideally don't run other tests "
+                         << "as root, tho.";
+  // True if the post-install action is expected to succeed.
+  bool should_succeed = do_losetup && !err_code;
+
+  string orig_cwd;
+  {
+    vector<char> buf(1000);
+    ASSERT_EQ(buf.data(), getcwd(buf.data(), buf.size()));
+    orig_cwd = string(buf.data(), strlen(buf.data()));
+  }
+
+  // Create a unique named working directory and chdir into it.
+  string cwd;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          "postinstall_runner_action_unittest-XXXXXX",
+          &cwd));
+  ASSERT_EQ(0, test_utils::Chdir(cwd));
+
+  // Create a 10MiB sparse file to be used as image; format it as ext2.
+  ASSERT_EQ(0, System(
+          "dd if=/dev/zero of=image.dat seek=10485759 bs=1 count=1 "
+          "status=none"));
+  ASSERT_EQ(0, System("mkfs.ext2 -F image.dat"));
+
+  // Create a uniquely named image mount point, mount the image.
+  ASSERT_EQ(0, System(string("mkdir -p ") + kStatefulPartition));
+  string mountpoint;
+  ASSERT_TRUE(utils::MakeTempDirectory(
+          string(kStatefulPartition) + "/" + kImageMountPointTemplate,
+          &mountpoint));
+  ASSERT_EQ(0, System(string("mount -o loop image.dat ") + mountpoint));
+
+  // Generate a fake postinst script inside the image.
+  string script = (err_code ?
+                   base::StringPrintf("#!/bin/bash\nexit %d", err_code) :
+                   base::StringPrintf(
+                       "#!/bin/bash\n"
+                       "mount | grep au_postint_mount | grep ext2\n"
+                       "if [ $? -eq 0 ]; then\n"
+                       "  touch %s/postinst_called\n"
+                       "fi\n",
+                       cwd.c_str()));
+  const string script_file_name = mountpoint + "/postinst";
+  ASSERT_TRUE(WriteFileString(script_file_name, script));
+  ASSERT_EQ(0, System(string("chmod a+x ") + script_file_name));
+
+  // Unmount image; do not remove the uniquely named directory as it will be
+  // reused during the test.
+  ASSERT_TRUE(utils::UnmountFilesystem(mountpoint));
+
+  // get a loop device we can use for the install device
+  string dev = "/dev/null";
+
+  unique_ptr<test_utils::ScopedLoopbackDeviceBinder> loop_releaser;
+  if (do_losetup) {
+    loop_releaser.reset(new test_utils::ScopedLoopbackDeviceBinder(
+            cwd + "/image.dat", &dev));
+  }
+
+  // We use a test-specific powerwash marker file, to avoid race conditions.
+  string powerwash_marker_file = mountpoint + "/factory_install_reset";
+  LOG(INFO) << ">>> powerwash_marker_file=" << powerwash_marker_file;
+
+  ActionProcessor processor;
+  ObjectFeederAction<InstallPlan> feeder_action;
+  InstallPlan::Partition part;
+  part.name = "part";
+  part.target_path = dev;
+  part.run_postinstall = true;
+  InstallPlan install_plan;
+  install_plan.partitions = {part};
+  install_plan.download_url = "http://devserver:8080/update";
+  install_plan.powerwash_required = powerwash_required;
+  feeder_action.set_obj(install_plan);
+  PostinstallRunnerAction runner_action(&fake_boot_control_,
+                                        powerwash_marker_file.c_str());
+  BondActions(&feeder_action, &runner_action);
+  ObjectCollectorAction<InstallPlan> collector_action;
+  BondActions(&runner_action, &collector_action);
+  PostinstActionProcessorDelegate delegate;
+  processor.EnqueueAction(&feeder_action);
+  processor.EnqueueAction(&runner_action);
+  processor.EnqueueAction(&collector_action);
+  processor.set_delegate(&delegate);
+
+  loop_.PostTask(FROM_HERE,
+                 base::Bind([&processor] { processor.StartProcessing(); }));
+  loop_.Run();
+  ASSERT_FALSE(processor.IsRunning());
+
+  EXPECT_TRUE(delegate.code_set_);
+  EXPECT_EQ(should_succeed, delegate.code_ == ErrorCode::kSuccess);
+  if (should_succeed)
+    EXPECT_TRUE(install_plan == collector_action.object());
+
+  const base::FilePath kPowerwashMarkerPath(powerwash_marker_file);
+  string actual_cmd;
+  if (should_succeed && powerwash_required) {
+    EXPECT_TRUE(base::ReadFileToString(kPowerwashMarkerPath, &actual_cmd));
+    EXPECT_EQ(kPowerwashCommand, actual_cmd);
+  } else {
+    EXPECT_FALSE(
+        base::ReadFileToString(kPowerwashMarkerPath, &actual_cmd));
+  }
+
+  if (err_code == 2)
+    EXPECT_EQ(ErrorCode::kPostinstallBootedFromFirmwareB, delegate.code_);
+
+  struct stat stbuf;
+  int rc = lstat((string(cwd) + "/postinst_called").c_str(), &stbuf);
+  if (should_succeed)
+    ASSERT_EQ(0, rc);
+  else
+    ASSERT_LT(rc, 0);
+
+  if (do_losetup) {
+    loop_releaser.reset(nullptr);
+  }
+
+  // Remove unique stateful directory.
+  ASSERT_EQ(0, System(string("rm -fr ") + mountpoint));
+
+  // Remove the temporary work directory.
+  ASSERT_EQ(0, test_utils::Chdir(orig_cwd));
+  ASSERT_EQ(0, System(string("rm -fr ") + cwd));
+}
+
+// Death tests don't seem to be working on Hardy
+TEST_F(PostinstallRunnerActionTest, DISABLED_RunAsRootDeathTest) {
+  ASSERT_EQ(0, getuid());
+  PostinstallRunnerAction runner_action(&fake_boot_control_);
+  ASSERT_DEATH({ runner_action.TerminateProcessing(); },
+               "postinstall_runner_action.h:.*] Check failed");
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/xz_extent_writer.cc b/payload_consumer/xz_extent_writer.cc
new file mode 100644
index 0000000..4bd893d
--- /dev/null
+++ b/payload_consumer/xz_extent_writer.cc
@@ -0,0 +1,118 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_consumer/xz_extent_writer.h"
+
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+const brillo::Blob::size_type kOutputBufferLength = 16 * 1024;
+
+// xz uses a variable dictionary size which impacts on the compression ratio
+// and is required to be reconstructed in RAM during decompression. While we
+// control the required memory from the compressor side, the decompressor allows
+// to set a limit on this dictionary size, rejecting compressed streams that
+// require more than that. "xz -9" requires up to 64 MiB, so a 64 MiB limit
+// will allow compressed streams up to -9, the maximum compression setting.
+const uint32_t kXzMaxDictSize = 64 * 1024 * 1024;
+
+const char* XzErrorString(enum xz_ret error) {
+  #define __XZ_ERROR_STRING_CASE(code) case code: return #code;
+  switch (error) {
+    __XZ_ERROR_STRING_CASE(XZ_OK)
+    __XZ_ERROR_STRING_CASE(XZ_STREAM_END)
+    __XZ_ERROR_STRING_CASE(XZ_UNSUPPORTED_CHECK)
+    __XZ_ERROR_STRING_CASE(XZ_MEM_ERROR)
+    __XZ_ERROR_STRING_CASE(XZ_MEMLIMIT_ERROR)
+    __XZ_ERROR_STRING_CASE(XZ_FORMAT_ERROR)
+    __XZ_ERROR_STRING_CASE(XZ_OPTIONS_ERROR)
+    __XZ_ERROR_STRING_CASE(XZ_DATA_ERROR)
+    __XZ_ERROR_STRING_CASE(XZ_BUF_ERROR)
+    default:
+      return "<unknown xz error>";
+  }
+  #undef __XZ_ERROR_STRING_CASE
+};
+}  // namespace
+
+XzExtentWriter::~XzExtentWriter() {
+  xz_dec_end(stream_);
+}
+
+bool XzExtentWriter::Init(FileDescriptorPtr fd,
+                          const vector<Extent>& extents,
+                          uint32_t block_size) {
+  stream_ = xz_dec_init(XZ_DYNALLOC, kXzMaxDictSize);
+  TEST_AND_RETURN_FALSE(stream_ != nullptr);
+  return underlying_writer_->Init(fd, extents, block_size);
+}
+
+bool XzExtentWriter::Write(const void* bytes, size_t count) {
+  // Copy the input data into |input_buffer_| only if |input_buffer_| already
+  // contains unconsumed data. Otherwise, process the data directly from the
+  // source.
+  const uint8_t* input = reinterpret_cast<const uint8_t*>(bytes);
+  if (!input_buffer_.empty()) {
+    input_buffer_.insert(input_buffer_.end(), input, input + count);
+    input = input_buffer_.data();
+    count = input_buffer_.size();
+  }
+
+  xz_buf request;
+  request.in = input;
+  request.in_pos = 0;
+  request.in_size = count;
+
+  brillo::Blob output_buffer(kOutputBufferLength);
+  request.out = output_buffer.data();
+  request.out_size = output_buffer.size();
+  for (;;) {
+    request.out_pos = 0;
+
+    xz_ret ret = xz_dec_run(stream_, &request);
+    if (ret != XZ_OK && ret != XZ_STREAM_END) {
+      LOG(ERROR) << "xz_dec_run returned " << XzErrorString(ret);
+      return false;
+    }
+
+    if (request.out_pos == 0)
+      break;
+
+    TEST_AND_RETURN_FALSE(
+        underlying_writer_->Write(output_buffer.data(), request.out_pos));
+    if (ret == XZ_STREAM_END)
+      CHECK_EQ(request.in_size, request.in_pos);
+    if (request.in_size == request.in_pos)
+      break;  // No more input to process.
+  }
+  output_buffer.clear();
+
+  // Store unconsumed data (if any) in |input_buffer_|. Since |input| can point
+  // to the existing |input_buffer_| we create a new one before assigning it.
+  brillo::Blob new_input_buffer(request.in + request.in_pos,
+                                request.in + request.in_size);
+  input_buffer_ = std::move(new_input_buffer);
+  return true;
+}
+
+bool XzExtentWriter::EndImpl() {
+  TEST_AND_RETURN_FALSE(input_buffer_.empty());
+  return underlying_writer_->End();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_consumer/xz_extent_writer.h b/payload_consumer/xz_extent_writer.h
new file mode 100644
index 0000000..a6b3257
--- /dev/null
+++ b/payload_consumer/xz_extent_writer.h
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_CONSUMER_XZ_EXTENT_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_CONSUMER_XZ_EXTENT_WRITER_H_
+
+#include <xz.h>
+
+#include <memory>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_consumer/extent_writer.h"
+
+// XzExtentWriter is a concrete ExtentWriter subclass that xz-decompresses
+// what it's given in Write using xz-embedded. Note that xz-embedded only
+// supports files with either no CRC or CRC-32. It passes the decompressed data
+// to an underlying ExtentWriter.
+
+namespace chromeos_update_engine {
+
+class XzExtentWriter : public ExtentWriter {
+ public:
+  explicit XzExtentWriter(std::unique_ptr<ExtentWriter> underlying_writer)
+      : underlying_writer_(std::move(underlying_writer)) {}
+  ~XzExtentWriter() override;
+
+  bool Init(FileDescriptorPtr fd,
+            const std::vector<Extent>& extents,
+            uint32_t block_size) override;
+  bool Write(const void* bytes, size_t count) override;
+  bool EndImpl() override;
+
+ private:
+  // The underlying ExtentWriter.
+  std::unique_ptr<ExtentWriter> underlying_writer_;
+  // The opaque xz decompressor struct.
+  xz_dec* stream_{nullptr};
+  brillo::Blob input_buffer_;
+
+  DISALLOW_COPY_AND_ASSIGN(XzExtentWriter);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_CONSUMER_XZ_EXTENT_WRITER_H_
diff --git a/payload_consumer/xz_extent_writer_unittest.cc b/payload_consumer/xz_extent_writer_unittest.cc
new file mode 100644
index 0000000..fb8bb40
--- /dev/null
+++ b/payload_consumer/xz_extent_writer_unittest.cc
@@ -0,0 +1,165 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_consumer/xz_extent_writer.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <brillo/make_unique_ptr.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/fake_extent_writer.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+const char kSampleData[] = "Redundaaaaaaaaaaaaaant\n";
+
+// Compressed data with CRC-32 check, generated with:
+// echo "Redundaaaaaaaaaaaaaant" | xz -9 --check=crc32 |
+// hexdump -v -e '"    " 12/1 "0x%02x, " "\n"'
+const uint8_t kCompressedDataCRC32[] = {
+    0xfd, 0x37, 0x7a, 0x58, 0x5a, 0x00, 0x00, 0x01, 0x69, 0x22, 0xde, 0x36,
+    0x02, 0x00, 0x21, 0x01, 0x1c, 0x00, 0x00, 0x00, 0x10, 0xcf, 0x58, 0xcc,
+    0xe0, 0x00, 0x16, 0x00, 0x10, 0x5d, 0x00, 0x29, 0x19, 0x48, 0x87, 0x88,
+    0xec, 0x49, 0x88, 0x73, 0x8b, 0x5d, 0xa6, 0x46, 0xb4, 0x00, 0x00, 0x00,
+    0x68, 0xfc, 0x7b, 0x25, 0x00, 0x01, 0x28, 0x17, 0x46, 0x9e, 0x08, 0xfe,
+    0x90, 0x42, 0x99, 0x0d, 0x01, 0x00, 0x00, 0x00, 0x00, 0x01, 0x59, 0x5a,
+};
+
+// Compressed data without checksum, generated with:
+// echo "Redundaaaaaaaaaaaaaant" | xz -9 --check=none |
+// hexdump -v -e '"    " 12/1 "0x%02x, " "\n"'
+const uint8_t kCompressedDataNoCheck[] = {
+    0xfd, 0x37, 0x7a, 0x58, 0x5a, 0x00, 0x00, 0x00, 0xff, 0x12, 0xd9, 0x41,
+    0x02, 0x00, 0x21, 0x01, 0x1c, 0x00, 0x00, 0x00, 0x10, 0xcf, 0x58, 0xcc,
+    0xe0, 0x00, 0x16, 0x00, 0x10, 0x5d, 0x00, 0x29, 0x19, 0x48, 0x87, 0x88,
+    0xec, 0x49, 0x88, 0x73, 0x8b, 0x5d, 0xa6, 0x46, 0xb4, 0x00, 0x00, 0x00,
+    0x00, 0x01, 0x24, 0x17, 0x4a, 0xd1, 0xbd, 0x52, 0x06, 0x72, 0x9e, 0x7a,
+    0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x59, 0x5a,
+};
+
+// Highly redundant data bigger than the internal buffer, generated with:
+// dd if=/dev/zero bs=30K count=1 | tr '\0' 'a' | xz -9 --check=crc32 |
+// hexdump -v -e '"    " 12/1 "0x%02x, " "\n"'
+const uint8_t kCompressed30KiBofA[] = {
+    0xfd, 0x37, 0x7a, 0x58, 0x5a, 0x00, 0x00, 0x01, 0x69, 0x22, 0xde, 0x36,
+    0x02, 0x00, 0x21, 0x01, 0x1c, 0x00, 0x00, 0x00, 0x10, 0xcf, 0x58, 0xcc,
+    0xe0, 0x77, 0xff, 0x00, 0x41, 0x5d, 0x00, 0x30, 0xef, 0xfb, 0xbf, 0xfe,
+    0xa3, 0xb1, 0x5e, 0xe5, 0xf8, 0x3f, 0xb2, 0xaa, 0x26, 0x55, 0xf8, 0x68,
+    0x70, 0x41, 0x70, 0x15, 0x0f, 0x8d, 0xfd, 0x1e, 0x4c, 0x1b, 0x8a, 0x42,
+    0xb7, 0x19, 0xf4, 0x69, 0x18, 0x71, 0xae, 0x66, 0x23, 0x8a, 0x8a, 0x4d,
+    0x2f, 0xa3, 0x0d, 0xd9, 0x7f, 0xa6, 0xe3, 0x8c, 0x23, 0x11, 0x53, 0xe0,
+    0x59, 0x18, 0xc5, 0x75, 0x8a, 0xe2, 0x76, 0x4c, 0xee, 0x30, 0x00, 0x00,
+    0x00, 0x00, 0x00, 0x00, 0xf9, 0x47, 0xb5, 0xee, 0x00, 0x01, 0x59, 0x80,
+    0xf0, 0x01, 0x00, 0x00, 0xe0, 0x41, 0x96, 0xde, 0x3e, 0x30, 0x0d, 0x8b,
+    0x02, 0x00, 0x00, 0x00, 0x00, 0x01, 0x59, 0x5a,
+};
+
+}  // namespace
+
+class XzExtentWriterTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    fake_extent_writer_ = new FakeExtentWriter();
+    xz_writer_.reset(
+        new XzExtentWriter(brillo::make_unique_ptr(fake_extent_writer_)));
+  }
+
+  void WriteAll(const brillo::Blob& compressed) {
+    EXPECT_TRUE(xz_writer_->Init(fd_, {}, 1024));
+    EXPECT_TRUE(xz_writer_->Write(compressed.data(), compressed.size()));
+    EXPECT_TRUE(xz_writer_->End());
+
+    EXPECT_TRUE(fake_extent_writer_->InitCalled());
+    EXPECT_TRUE(fake_extent_writer_->EndCalled());
+  }
+
+  // Owned by |xz_writer_|. This object is invalidated after |xz_writer_| is
+  // deleted.
+  FakeExtentWriter* fake_extent_writer_{nullptr};
+  std::unique_ptr<XzExtentWriter> xz_writer_;
+
+  const brillo::Blob sample_data_{
+      std::begin(kSampleData),
+      std::begin(kSampleData) + strlen(kSampleData)};
+  FileDescriptorPtr fd_;
+};
+
+TEST_F(XzExtentWriterTest, CreateAndDestroy) {
+  // Test that no Init() or End() called doesn't crash the program.
+  EXPECT_FALSE(fake_extent_writer_->InitCalled());
+  EXPECT_FALSE(fake_extent_writer_->EndCalled());
+}
+
+TEST_F(XzExtentWriterTest, CompressedSampleData) {
+  WriteAll(brillo::Blob(std::begin(kCompressedDataNoCheck),
+                          std::end(kCompressedDataNoCheck)));
+  EXPECT_EQ(sample_data_, fake_extent_writer_->WrittenData());
+}
+
+TEST_F(XzExtentWriterTest, CompressedSampleDataWithCrc) {
+  WriteAll(brillo::Blob(std::begin(kCompressedDataCRC32),
+                          std::end(kCompressedDataCRC32)));
+  EXPECT_EQ(sample_data_, fake_extent_writer_->WrittenData());
+}
+
+TEST_F(XzExtentWriterTest, CompressedDataBiggerThanTheBuffer) {
+  // Test that even if the output data is bigger than the internal buffer, all
+  // the data is written.
+  WriteAll(brillo::Blob(std::begin(kCompressed30KiBofA),
+                          std::end(kCompressed30KiBofA)));
+  brillo::Blob expected_data(30 * 1024, 'a');
+  EXPECT_EQ(expected_data, fake_extent_writer_->WrittenData());
+}
+
+TEST_F(XzExtentWriterTest, GarbageDataRejected) {
+  EXPECT_TRUE(xz_writer_->Init(fd_, {}, 1024));
+  // The sample_data_ is an uncompressed string.
+  EXPECT_FALSE(xz_writer_->Write(sample_data_.data(), sample_data_.size()));
+  EXPECT_TRUE(xz_writer_->End());
+
+  EXPECT_TRUE(fake_extent_writer_->EndCalled());
+}
+
+TEST_F(XzExtentWriterTest, PartialDataIsKept) {
+  brillo::Blob compressed(std::begin(kCompressed30KiBofA),
+                            std::end(kCompressed30KiBofA));
+  EXPECT_TRUE(xz_writer_->Init(fd_, {}, 1024));
+  for (uint8_t byte : compressed) {
+    EXPECT_TRUE(xz_writer_->Write(&byte, 1));
+  }
+  EXPECT_TRUE(xz_writer_->End());
+
+  // The sample_data_ is an uncompressed string.
+  brillo::Blob expected_data(30 * 1024, 'a');
+  EXPECT_EQ(expected_data, fake_extent_writer_->WrittenData());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/ab_generator.cc b/payload_generator/ab_generator.cc
new file mode 100644
index 0000000..7caf897
--- /dev/null
+++ b/payload_generator/ab_generator.cc
@@ -0,0 +1,334 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/ab_generator.h"
+
+#include <algorithm>
+
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/bzip.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/delta_diff_utils.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+bool ABGenerator::GenerateOperations(
+    const PayloadGenerationConfig& config,
+    const PartitionConfig& old_part,
+    const PartitionConfig& new_part,
+    BlobFileWriter* blob_file,
+    vector<AnnotatedOperation>* aops) {
+  TEST_AND_RETURN_FALSE(old_part.name == new_part.name);
+
+  ssize_t hard_chunk_blocks = (config.hard_chunk_size == -1 ? -1 :
+                               config.hard_chunk_size / config.block_size);
+  size_t soft_chunk_blocks = config.soft_chunk_size / config.block_size;
+
+  aops->clear();
+  TEST_AND_RETURN_FALSE(diff_utils::DeltaReadPartition(
+      aops,
+      old_part,
+      new_part,
+      hard_chunk_blocks,
+      soft_chunk_blocks,
+      blob_file,
+      true));  // src_ops_allowed
+  LOG(INFO) << "done reading " << new_part.name;
+
+  TEST_AND_RETURN_FALSE(FragmentOperations(aops,
+                                           new_part.path,
+                                           blob_file));
+  SortOperationsByDestination(aops);
+
+  // Use the soft_chunk_size when merging operations to prevent merging all
+  // the operations into a huge one if there's no hard limit.
+  size_t merge_chunk_blocks = soft_chunk_blocks;
+  if (hard_chunk_blocks != -1 &&
+      static_cast<size_t>(hard_chunk_blocks) < soft_chunk_blocks) {
+    merge_chunk_blocks = hard_chunk_blocks;
+  }
+
+  TEST_AND_RETURN_FALSE(MergeOperations(aops,
+                                        merge_chunk_blocks,
+                                        new_part.path,
+                                        blob_file));
+
+  if (config.minor_version == kOpSrcHashMinorPayloadVersion)
+    TEST_AND_RETURN_FALSE(AddSourceHash(aops, old_part.path));
+
+  return true;
+}
+
+void ABGenerator::SortOperationsByDestination(
+    vector<AnnotatedOperation>* aops) {
+  sort(aops->begin(), aops->end(), diff_utils::CompareAopsByDestination);
+}
+
+bool ABGenerator::FragmentOperations(
+    vector<AnnotatedOperation>* aops,
+    const string& target_part_path,
+    BlobFileWriter* blob_file) {
+  vector<AnnotatedOperation> fragmented_aops;
+  for (const AnnotatedOperation& aop : *aops) {
+    if (aop.op.type() == InstallOperation::SOURCE_COPY) {
+      TEST_AND_RETURN_FALSE(SplitSourceCopy(aop, &fragmented_aops));
+    } else if ((aop.op.type() == InstallOperation::REPLACE) ||
+               (aop.op.type() == InstallOperation::REPLACE_BZ)) {
+      TEST_AND_RETURN_FALSE(SplitReplaceOrReplaceBz(aop, &fragmented_aops,
+                                                    target_part_path,
+                                                    blob_file));
+    } else {
+      fragmented_aops.push_back(aop);
+    }
+  }
+  *aops = fragmented_aops;
+  return true;
+}
+
+bool ABGenerator::SplitSourceCopy(
+    const AnnotatedOperation& original_aop,
+    vector<AnnotatedOperation>* result_aops) {
+  InstallOperation original_op = original_aop.op;
+  TEST_AND_RETURN_FALSE(original_op.type() == InstallOperation::SOURCE_COPY);
+  // Keeps track of the index of curr_src_ext.
+  int curr_src_ext_index = 0;
+  Extent curr_src_ext = original_op.src_extents(curr_src_ext_index);
+  for (int i = 0; i < original_op.dst_extents_size(); i++) {
+    Extent dst_ext = original_op.dst_extents(i);
+    // The new operation which will have only one dst extent.
+    InstallOperation new_op;
+    uint64_t blocks_left = dst_ext.num_blocks();
+    while (blocks_left > 0) {
+      if (curr_src_ext.num_blocks() <= blocks_left) {
+        // If the curr_src_ext is smaller than dst_ext, add it.
+        blocks_left -= curr_src_ext.num_blocks();
+        *(new_op.add_src_extents()) = curr_src_ext;
+        if (curr_src_ext_index + 1 < original_op.src_extents().size()) {
+          curr_src_ext = original_op.src_extents(++curr_src_ext_index);
+        } else {
+          break;
+        }
+      } else {
+        // Split src_exts that are bigger than the dst_ext we're dealing with.
+        Extent first_ext;
+        first_ext.set_num_blocks(blocks_left);
+        first_ext.set_start_block(curr_src_ext.start_block());
+        *(new_op.add_src_extents()) = first_ext;
+        // Keep the second half of the split op.
+        curr_src_ext.set_num_blocks(curr_src_ext.num_blocks() - blocks_left);
+        curr_src_ext.set_start_block(curr_src_ext.start_block() + blocks_left);
+        blocks_left -= first_ext.num_blocks();
+      }
+    }
+    // Fix up our new operation and add it to the results.
+    new_op.set_type(InstallOperation::SOURCE_COPY);
+    *(new_op.add_dst_extents()) = dst_ext;
+    new_op.set_src_length(dst_ext.num_blocks() * kBlockSize);
+    new_op.set_dst_length(dst_ext.num_blocks() * kBlockSize);
+
+    AnnotatedOperation new_aop;
+    new_aop.op = new_op;
+    new_aop.name = base::StringPrintf("%s:%d", original_aop.name.c_str(), i);
+    result_aops->push_back(new_aop);
+  }
+  if (curr_src_ext_index != original_op.src_extents().size() - 1) {
+    LOG(FATAL) << "Incorrectly split SOURCE_COPY operation. Did not use all "
+               << "source extents.";
+  }
+  return true;
+}
+
+bool ABGenerator::SplitReplaceOrReplaceBz(
+    const AnnotatedOperation& original_aop,
+    vector<AnnotatedOperation>* result_aops,
+    const string& target_part_path,
+    BlobFileWriter* blob_file) {
+  InstallOperation original_op = original_aop.op;
+  const bool is_replace = original_op.type() == InstallOperation::REPLACE;
+  TEST_AND_RETURN_FALSE(is_replace ||
+                        original_op.type() == InstallOperation::REPLACE_BZ);
+
+  uint32_t data_offset = original_op.data_offset();
+  for (int i = 0; i < original_op.dst_extents_size(); i++) {
+    Extent dst_ext = original_op.dst_extents(i);
+    // Make a new operation with only one dst extent.
+    InstallOperation new_op;
+    *(new_op.add_dst_extents()) = dst_ext;
+    uint32_t data_size = dst_ext.num_blocks() * kBlockSize;
+    new_op.set_dst_length(data_size);
+    // If this is a REPLACE, attempt to reuse portions of the existing blob.
+    if (is_replace) {
+      new_op.set_type(InstallOperation::REPLACE);
+      new_op.set_data_length(data_size);
+      new_op.set_data_offset(data_offset);
+      data_offset += data_size;
+    }
+
+    AnnotatedOperation new_aop;
+    new_aop.op = new_op;
+    new_aop.name = base::StringPrintf("%s:%d", original_aop.name.c_str(), i);
+    TEST_AND_RETURN_FALSE(AddDataAndSetType(&new_aop, target_part_path,
+                                            blob_file));
+
+    result_aops->push_back(new_aop);
+  }
+  return true;
+}
+
+bool ABGenerator::MergeOperations(vector<AnnotatedOperation>* aops,
+                                  size_t chunk_blocks,
+                                  const string& target_part_path,
+                                  BlobFileWriter* blob_file) {
+  vector<AnnotatedOperation> new_aops;
+  for (const AnnotatedOperation& curr_aop : *aops) {
+    if (new_aops.empty()) {
+      new_aops.push_back(curr_aop);
+      continue;
+    }
+    AnnotatedOperation& last_aop = new_aops.back();
+
+    if (last_aop.op.dst_extents_size() <= 0 ||
+        curr_aop.op.dst_extents_size() <= 0) {
+      new_aops.push_back(curr_aop);
+      continue;
+    }
+    uint32_t last_dst_idx = last_aop.op.dst_extents_size() - 1;
+    uint32_t last_end_block =
+        last_aop.op.dst_extents(last_dst_idx).start_block() +
+        last_aop.op.dst_extents(last_dst_idx).num_blocks();
+    uint32_t curr_start_block = curr_aop.op.dst_extents(0).start_block();
+    uint32_t combined_block_count =
+        last_aop.op.dst_extents(last_dst_idx).num_blocks() +
+        curr_aop.op.dst_extents(0).num_blocks();
+    bool good_op_type = curr_aop.op.type() == InstallOperation::SOURCE_COPY ||
+                        curr_aop.op.type() == InstallOperation::REPLACE ||
+                        curr_aop.op.type() == InstallOperation::REPLACE_BZ;
+    if (good_op_type &&
+        last_aop.op.type() == curr_aop.op.type() &&
+        last_end_block == curr_start_block &&
+        combined_block_count <= chunk_blocks) {
+      // If the operations have the same type (which is a type that we can
+      // merge), are contiguous, are fragmented to have one destination extent,
+      // and their combined block count would be less than chunk size, merge
+      // them.
+      last_aop.name = base::StringPrintf("%s,%s",
+                                         last_aop.name.c_str(),
+                                         curr_aop.name.c_str());
+
+      ExtendExtents(last_aop.op.mutable_src_extents(),
+                    curr_aop.op.src_extents());
+      if (curr_aop.op.src_length() > 0)
+        last_aop.op.set_src_length(last_aop.op.src_length() +
+                                   curr_aop.op.src_length());
+      ExtendExtents(last_aop.op.mutable_dst_extents(),
+                    curr_aop.op.dst_extents());
+      if (curr_aop.op.dst_length() > 0)
+        last_aop.op.set_dst_length(last_aop.op.dst_length() +
+                                   curr_aop.op.dst_length());
+      // Set the data length to zero so we know to add the blob later.
+      if (curr_aop.op.type() == InstallOperation::REPLACE ||
+          curr_aop.op.type() == InstallOperation::REPLACE_BZ) {
+        last_aop.op.set_data_length(0);
+      }
+    } else {
+      // Otherwise just include the extent as is.
+      new_aops.push_back(curr_aop);
+    }
+  }
+
+  // Set the blobs for REPLACE/REPLACE_BZ operations that have been merged.
+  for (AnnotatedOperation& curr_aop : new_aops) {
+    if (curr_aop.op.data_length() == 0 &&
+        (curr_aop.op.type() == InstallOperation::REPLACE ||
+         curr_aop.op.type() == InstallOperation::REPLACE_BZ)) {
+      TEST_AND_RETURN_FALSE(AddDataAndSetType(&curr_aop, target_part_path,
+                                              blob_file));
+    }
+  }
+
+  *aops = new_aops;
+  return true;
+}
+
+bool ABGenerator::AddDataAndSetType(AnnotatedOperation* aop,
+                                    const string& target_part_path,
+                                    BlobFileWriter* blob_file) {
+  TEST_AND_RETURN_FALSE(aop->op.type() == InstallOperation::REPLACE ||
+                        aop->op.type() == InstallOperation::REPLACE_BZ);
+
+  brillo::Blob data(aop->op.dst_length());
+  vector<Extent> dst_extents;
+  ExtentsToVector(aop->op.dst_extents(), &dst_extents);
+  TEST_AND_RETURN_FALSE(utils::ReadExtents(target_part_path,
+                                           dst_extents,
+                                           &data,
+                                           data.size(),
+                                           kBlockSize));
+
+  brillo::Blob data_bz;
+  TEST_AND_RETURN_FALSE(BzipCompress(data, &data_bz));
+  CHECK(!data_bz.empty());
+
+  brillo::Blob* data_p = nullptr;
+  InstallOperation_Type new_op_type;
+  if (data_bz.size() < data.size()) {
+    new_op_type = InstallOperation::REPLACE_BZ;
+    data_p = &data_bz;
+  } else {
+    new_op_type = InstallOperation::REPLACE;
+    data_p = &data;
+  }
+
+  // If the operation doesn't point to a data blob, then we add it.
+  if (aop->op.type() != new_op_type ||
+      aop->op.data_length() != data_p->size()) {
+    aop->op.set_type(new_op_type);
+    aop->SetOperationBlob(data_p, blob_file);
+  }
+
+  return true;
+}
+
+bool ABGenerator::AddSourceHash(vector<AnnotatedOperation>* aops,
+                                const string& source_part_path) {
+  for (AnnotatedOperation& aop : *aops) {
+    if (aop.op.src_extents_size() == 0)
+      continue;
+
+    vector<Extent> src_extents;
+    ExtentsToVector(aop.op.src_extents(), &src_extents);
+    brillo::Blob src_data, src_hash;
+    uint64_t src_length =
+        aop.op.has_src_length()
+            ? aop.op.src_length()
+            : BlocksInExtents(aop.op.src_extents()) * kBlockSize;
+    TEST_AND_RETURN_FALSE(utils::ReadExtents(
+        source_part_path, src_extents, &src_data, src_length, kBlockSize));
+    TEST_AND_RETURN_FALSE(HashCalculator::RawHashOfData(src_data, &src_hash));
+    aop.op.set_src_sha256_hash(src_hash.data(), src_hash.size());
+  }
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/ab_generator.h b/payload_generator/ab_generator.h
new file mode 100644
index 0000000..c2837c0
--- /dev/null
+++ b/payload_generator/ab_generator.h
@@ -0,0 +1,132 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_AB_GENERATOR_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_AB_GENERATOR_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/payload_generator/extent_utils.h"
+#include "update_engine/payload_generator/filesystem_interface.h"
+#include "update_engine/payload_generator/operations_generator.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+// The ABGenerator is an operations generator that generates payloads using the
+// A-to-B operations SOURCE_COPY and SOURCE_BSDIFF introduced in the payload
+// minor version 2 format.
+class ABGenerator : public OperationsGenerator {
+ public:
+  ABGenerator() = default;
+
+  // Generate the update payload operations for the given partition using
+  // SOURCE_* operations, used for generating deltas for the minor version
+  // kSourceMinorPayloadVersion. This function will generate operations in the
+  // partition that will read blocks from the source partition in random order
+  // and write the new image on the target partition, also possibly in random
+  // order. The operations are stored in |aops| and should be executed in that
+  // order. All the offsets in the operations reference the data written to
+  // |blob_file|.
+  bool GenerateOperations(
+      const PayloadGenerationConfig& config,
+      const PartitionConfig& old_part,
+      const PartitionConfig& new_part,
+      BlobFileWriter* blob_file,
+      std::vector<AnnotatedOperation>* aops) override;
+
+  // Split the operations in the vector of AnnotatedOperations |aops|
+  // such that for every operation there is only one dst extent and updates
+  // |aops| with the new list of operations. All kinds of operations are
+  // fragmented except BSDIFF and SOURCE_BSDIFF operations.
+  // The |target_part_path| is the filename of the new image, where the
+  // destination extents refer to. The blobs of the operations in |aops| should
+  // reference |blob_file|. |blob_file| are updated if needed.
+  static bool FragmentOperations(std::vector<AnnotatedOperation>* aops,
+                                 const std::string& target_part_path,
+                                 BlobFileWriter* blob_file);
+
+  // Takes a vector of AnnotatedOperations |aops| and sorts them by the first
+  // start block in their destination extents. Sets |aops| to a vector of the
+  // sorted operations.
+  static void SortOperationsByDestination(
+      std::vector<AnnotatedOperation>* aops);
+
+  // Takes an SOURCE_COPY install operation, |aop|, and adds one operation for
+  // each dst extent in |aop| to |ops|. The new operations added to |ops| will
+  // have only one dst extent. The src extents are split so the number of blocks
+  // in the src and dst extents are equal.
+  // E.g. we have a SOURCE_COPY operation:
+  //   src extents: [(1, 3), (5, 1), (7, 1)], dst extents: [(2, 2), (6, 3)]
+  // Then we will get 2 new operations:
+  //   1. src extents: [(1, 2)], dst extents: [(2, 2)]
+  //   2. src extents: [(3, 1),(5, 1),(7, 1)], dst extents: [(6, 3)]
+  static bool SplitSourceCopy(const AnnotatedOperation& original_aop,
+                              std::vector<AnnotatedOperation>* result_aops);
+
+  // Takes a REPLACE/REPLACE_BZ operation |aop|, and adds one operation for each
+  // dst extent in |aop| to |ops|. The new operations added to |ops| will have
+  // only one dst extent each, and may be either a REPLACE or REPLACE_BZ
+  // depending on whether compression is advantageous.
+  static bool SplitReplaceOrReplaceBz(
+      const AnnotatedOperation& original_aop,
+      std::vector<AnnotatedOperation>* result_aops,
+      const std::string& target_part,
+      BlobFileWriter* blob_file);
+
+  // Takes a sorted (by first destination extent) vector of operations |aops|
+  // and merges SOURCE_COPY, REPLACE, and REPLACE_BZ operations in that vector.
+  // It will merge two operations if:
+  //   - They are of the same type.
+  //   - They are contiguous.
+  //   - Their combined blocks do not exceed |chunk_blocks| blocks.
+  // Note that unlike other methods, you can't pass a negative number in
+  // |chunk_blocks|.
+  static bool MergeOperations(std::vector<AnnotatedOperation>* aops,
+                              size_t chunk_blocks,
+                              const std::string& target_part,
+                              BlobFileWriter* blob_file);
+
+  // Takes a vector of AnnotatedOperations |aops|, adds source hash to all
+  // operations that have src_extents.
+  static bool AddSourceHash(std::vector<AnnotatedOperation>* aops,
+                            const std::string& source_part_path);
+
+ private:
+  // Adds the data payload for a REPLACE/REPLACE_BZ operation |aop| by reading
+  // its output extents from |target_part_path| and appending a corresponding
+  // data blob to |data_fd|. The blob will be compressed if this is smaller than
+  // the uncompressed form, and the operation type will be set accordingly.
+  // |*blob_file| will be updated as well. If the operation happens to have
+  // the right type and already points to a data blob, nothing is written.
+  // Caller should only set type and data blob if it's valid.
+  static bool AddDataAndSetType(AnnotatedOperation* aop,
+                                const std::string& target_part_path,
+                                BlobFileWriter* blob_file);
+
+  DISALLOW_COPY_AND_ASSIGN(ABGenerator);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_AB_GENERATOR_H_
diff --git a/payload_generator/ab_generator_unittest.cc b/payload_generator/ab_generator_unittest.cc
new file mode 100644
index 0000000..632fc64
--- /dev/null
+++ b/payload_generator/ab_generator_unittest.cc
@@ -0,0 +1,590 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/ab_generator.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <string>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/bzip.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+bool ExtentEquals(Extent ext, uint64_t start_block, uint64_t num_blocks) {
+  return ext.start_block() == start_block && ext.num_blocks() == num_blocks;
+}
+
+// Tests splitting of a REPLACE/REPLACE_BZ operation.
+void TestSplitReplaceOrReplaceBzOperation(InstallOperation_Type orig_type,
+                                          bool compressible) {
+  const size_t op_ex1_start_block = 2;
+  const size_t op_ex1_num_blocks = 2;
+  const size_t op_ex2_start_block = 6;
+  const size_t op_ex2_num_blocks = 1;
+  const size_t part_num_blocks = 7;
+
+  // Create the target partition data.
+  string part_path;
+  EXPECT_TRUE(utils::MakeTempFile(
+      "SplitReplaceOrReplaceBzTest_part.XXXXXX", &part_path, nullptr));
+  ScopedPathUnlinker part_path_unlinker(part_path);
+  const size_t part_size = part_num_blocks * kBlockSize;
+  brillo::Blob part_data;
+  if (compressible) {
+    part_data.resize(part_size);
+    test_utils::FillWithData(&part_data);
+  } else {
+    std::mt19937 gen(12345);
+    std::uniform_int_distribution<uint8_t> dis(0, 255);
+    for (uint32_t i = 0; i < part_size; i++)
+      part_data.push_back(dis(gen));
+  }
+  ASSERT_EQ(part_size, part_data.size());
+  ASSERT_TRUE(utils::WriteFile(part_path.c_str(), part_data.data(), part_size));
+
+  // Create original operation and blob data.
+  const size_t op_ex1_offset = op_ex1_start_block * kBlockSize;
+  const size_t op_ex1_size = op_ex1_num_blocks * kBlockSize;
+  const size_t op_ex2_offset = op_ex2_start_block * kBlockSize;
+  const size_t op_ex2_size = op_ex2_num_blocks * kBlockSize;
+  InstallOperation op;
+  op.set_type(orig_type);
+  *(op.add_dst_extents()) = ExtentForRange(op_ex1_start_block,
+                                           op_ex1_num_blocks);
+  *(op.add_dst_extents()) = ExtentForRange(op_ex2_start_block,
+                                           op_ex2_num_blocks);
+  op.set_dst_length(op_ex1_num_blocks + op_ex2_num_blocks);
+
+  brillo::Blob op_data;
+  op_data.insert(op_data.end(),
+                 part_data.begin() + op_ex1_offset,
+                 part_data.begin() + op_ex1_offset + op_ex1_size);
+  op_data.insert(op_data.end(),
+                 part_data.begin() + op_ex2_offset,
+                 part_data.begin() + op_ex2_offset + op_ex2_size);
+  brillo::Blob op_blob;
+  if (orig_type == InstallOperation::REPLACE) {
+    op_blob = op_data;
+  } else {
+    ASSERT_TRUE(BzipCompress(op_data, &op_blob));
+  }
+  op.set_data_offset(0);
+  op.set_data_length(op_blob.size());
+
+  AnnotatedOperation aop;
+  aop.op = op;
+  aop.name = "SplitTestOp";
+
+  // Create the data file.
+  string data_path;
+  EXPECT_TRUE(utils::MakeTempFile(
+      "SplitReplaceOrReplaceBzTest_data.XXXXXX", &data_path, nullptr));
+  ScopedPathUnlinker data_path_unlinker(data_path);
+  int data_fd = open(data_path.c_str(), O_RDWR, 000);
+  EXPECT_GE(data_fd, 0);
+  ScopedFdCloser data_fd_closer(&data_fd);
+  EXPECT_TRUE(utils::WriteFile(data_path.c_str(), op_blob.data(),
+                               op_blob.size()));
+  off_t data_file_size = op_blob.size();
+  BlobFileWriter blob_file(data_fd, &data_file_size);
+
+  // Split the operation.
+  vector<AnnotatedOperation> result_ops;
+  ASSERT_TRUE(ABGenerator::SplitReplaceOrReplaceBz(
+          aop, &result_ops, part_path, &blob_file));
+
+  // Check the result.
+  InstallOperation_Type expected_type =
+      compressible ? InstallOperation::REPLACE_BZ : InstallOperation::REPLACE;
+
+  ASSERT_EQ(2, result_ops.size());
+
+  EXPECT_EQ("SplitTestOp:0", result_ops[0].name);
+  InstallOperation first_op = result_ops[0].op;
+  EXPECT_EQ(expected_type, first_op.type());
+  EXPECT_EQ(op_ex1_size, first_op.dst_length());
+  EXPECT_EQ(1, first_op.dst_extents().size());
+  EXPECT_TRUE(ExtentEquals(first_op.dst_extents(0), op_ex1_start_block,
+                           op_ex1_num_blocks));
+  // Obtain the expected blob.
+  brillo::Blob first_expected_data(
+      part_data.begin() + op_ex1_offset,
+      part_data.begin() + op_ex1_offset + op_ex1_size);
+  brillo::Blob first_expected_blob;
+  if (compressible) {
+    ASSERT_TRUE(BzipCompress(first_expected_data, &first_expected_blob));
+  } else {
+    first_expected_blob = first_expected_data;
+  }
+  EXPECT_EQ(first_expected_blob.size(), first_op.data_length());
+  // Check that the actual blob matches what's expected.
+  brillo::Blob first_data_blob(first_op.data_length());
+  ssize_t bytes_read;
+  ASSERT_TRUE(utils::PReadAll(data_fd,
+                              first_data_blob.data(),
+                              first_op.data_length(),
+                              first_op.data_offset(),
+                              &bytes_read));
+  ASSERT_EQ(bytes_read, first_op.data_length());
+  EXPECT_EQ(first_expected_blob, first_data_blob);
+
+  EXPECT_EQ("SplitTestOp:1", result_ops[1].name);
+  InstallOperation second_op = result_ops[1].op;
+  EXPECT_EQ(expected_type, second_op.type());
+  EXPECT_EQ(op_ex2_size, second_op.dst_length());
+  EXPECT_EQ(1, second_op.dst_extents().size());
+  EXPECT_TRUE(ExtentEquals(second_op.dst_extents(0), op_ex2_start_block,
+                           op_ex2_num_blocks));
+  // Obtain the expected blob.
+  brillo::Blob second_expected_data(
+      part_data.begin() + op_ex2_offset,
+      part_data.begin() + op_ex2_offset + op_ex2_size);
+  brillo::Blob second_expected_blob;
+  if (compressible) {
+    ASSERT_TRUE(BzipCompress(second_expected_data, &second_expected_blob));
+  } else {
+    second_expected_blob = second_expected_data;
+  }
+  EXPECT_EQ(second_expected_blob.size(), second_op.data_length());
+  // Check that the actual blob matches what's expected.
+  brillo::Blob second_data_blob(second_op.data_length());
+  ASSERT_TRUE(utils::PReadAll(data_fd,
+                              second_data_blob.data(),
+                              second_op.data_length(),
+                              second_op.data_offset(),
+                              &bytes_read));
+  ASSERT_EQ(bytes_read, second_op.data_length());
+  EXPECT_EQ(second_expected_blob, second_data_blob);
+
+  // Check relative layout of data blobs.
+  EXPECT_EQ(first_op.data_offset() + first_op.data_length(),
+            second_op.data_offset());
+  EXPECT_EQ(second_op.data_offset() + second_op.data_length(), data_file_size);
+  // If we split a REPLACE into multiple ones, ensure reuse of preexisting blob.
+  if (!compressible && orig_type == InstallOperation::REPLACE) {
+    EXPECT_EQ(0, first_op.data_offset());
+  }
+}
+
+// Tests merging of REPLACE/REPLACE_BZ operations.
+void TestMergeReplaceOrReplaceBzOperations(InstallOperation_Type orig_type,
+                                           bool compressible) {
+  const size_t first_op_num_blocks = 1;
+  const size_t second_op_num_blocks = 2;
+  const size_t total_op_num_blocks = first_op_num_blocks + second_op_num_blocks;
+  const size_t part_num_blocks = total_op_num_blocks + 2;
+
+  // Create the target partition data.
+  string part_path;
+  EXPECT_TRUE(utils::MakeTempFile(
+      "MergeReplaceOrReplaceBzTest_part.XXXXXX", &part_path, nullptr));
+  ScopedPathUnlinker part_path_unlinker(part_path);
+  const size_t part_size = part_num_blocks * kBlockSize;
+  brillo::Blob part_data;
+  if (compressible) {
+    part_data.resize(part_size);
+    test_utils::FillWithData(&part_data);
+  } else {
+    std::mt19937 gen(12345);
+    std::uniform_int_distribution<uint8_t> dis(0, 255);
+    for (uint32_t i = 0; i < part_size; i++)
+      part_data.push_back(dis(gen));
+  }
+  ASSERT_EQ(part_size, part_data.size());
+  ASSERT_TRUE(utils::WriteFile(part_path.c_str(), part_data.data(), part_size));
+
+  // Create original operations and blob data.
+  vector<AnnotatedOperation> aops;
+  brillo::Blob blob_data;
+  const size_t total_op_size = total_op_num_blocks * kBlockSize;
+
+  InstallOperation first_op;
+  first_op.set_type(orig_type);
+  const size_t first_op_size = first_op_num_blocks * kBlockSize;
+  first_op.set_dst_length(first_op_size);
+  *(first_op.add_dst_extents()) = ExtentForRange(0, first_op_num_blocks);
+  brillo::Blob first_op_data(part_data.begin(),
+                               part_data.begin() + first_op_size);
+  brillo::Blob first_op_blob;
+  if (orig_type == InstallOperation::REPLACE) {
+    first_op_blob = first_op_data;
+  } else {
+    ASSERT_TRUE(BzipCompress(first_op_data, &first_op_blob));
+  }
+  first_op.set_data_offset(0);
+  first_op.set_data_length(first_op_blob.size());
+  blob_data.insert(blob_data.end(), first_op_blob.begin(), first_op_blob.end());
+  AnnotatedOperation first_aop;
+  first_aop.op = first_op;
+  first_aop.name = "first";
+  aops.push_back(first_aop);
+
+  InstallOperation second_op;
+  second_op.set_type(orig_type);
+  const size_t second_op_size = second_op_num_blocks * kBlockSize;
+  second_op.set_dst_length(second_op_size);
+  *(second_op.add_dst_extents()) = ExtentForRange(first_op_num_blocks,
+                                                  second_op_num_blocks);
+  brillo::Blob second_op_data(part_data.begin() + first_op_size,
+                                part_data.begin() + total_op_size);
+  brillo::Blob second_op_blob;
+  if (orig_type == InstallOperation::REPLACE) {
+    second_op_blob = second_op_data;
+  } else {
+    ASSERT_TRUE(BzipCompress(second_op_data, &second_op_blob));
+  }
+  second_op.set_data_offset(first_op_blob.size());
+  second_op.set_data_length(second_op_blob.size());
+  blob_data.insert(blob_data.end(), second_op_blob.begin(),
+                   second_op_blob.end());
+  AnnotatedOperation second_aop;
+  second_aop.op = second_op;
+  second_aop.name = "second";
+  aops.push_back(second_aop);
+
+  // Create the data file.
+  string data_path;
+  EXPECT_TRUE(utils::MakeTempFile(
+      "MergeReplaceOrReplaceBzTest_data.XXXXXX", &data_path, nullptr));
+  ScopedPathUnlinker data_path_unlinker(data_path);
+  int data_fd = open(data_path.c_str(), O_RDWR, 000);
+  EXPECT_GE(data_fd, 0);
+  ScopedFdCloser data_fd_closer(&data_fd);
+  EXPECT_TRUE(utils::WriteFile(data_path.c_str(), blob_data.data(),
+                               blob_data.size()));
+  off_t data_file_size = blob_data.size();
+  BlobFileWriter blob_file(data_fd, &data_file_size);
+
+  // Merge the operations.
+  EXPECT_TRUE(ABGenerator::MergeOperations(
+      &aops, 5, part_path, &blob_file));
+
+  // Check the result.
+  InstallOperation_Type expected_op_type =
+      compressible ? InstallOperation::REPLACE_BZ : InstallOperation::REPLACE;
+  EXPECT_EQ(1, aops.size());
+  InstallOperation new_op = aops[0].op;
+  EXPECT_EQ(expected_op_type, new_op.type());
+  EXPECT_FALSE(new_op.has_src_length());
+  EXPECT_EQ(total_op_num_blocks * kBlockSize, new_op.dst_length());
+  EXPECT_EQ(1, new_op.dst_extents().size());
+  EXPECT_TRUE(ExtentEquals(new_op.dst_extents(0), 0, total_op_num_blocks));
+  EXPECT_EQ("first,second", aops[0].name);
+
+  // Check to see if the blob pointed to in the new extent has what we expect.
+  brillo::Blob expected_data(part_data.begin(),
+                               part_data.begin() + total_op_size);
+  brillo::Blob expected_blob;
+  if (compressible) {
+    ASSERT_TRUE(BzipCompress(expected_data, &expected_blob));
+  } else {
+    expected_blob = expected_data;
+  }
+  ASSERT_EQ(expected_blob.size(), new_op.data_length());
+  ASSERT_EQ(blob_data.size() + expected_blob.size(), data_file_size);
+  brillo::Blob new_op_blob(new_op.data_length());
+  ssize_t bytes_read;
+  ASSERT_TRUE(utils::PReadAll(data_fd,
+                              new_op_blob.data(),
+                              new_op.data_length(),
+                              new_op.data_offset(),
+                              &bytes_read));
+  ASSERT_EQ(new_op.data_length(), bytes_read);
+  EXPECT_EQ(expected_blob, new_op_blob);
+}
+
+}  // namespace
+
+class ABGeneratorTest : public ::testing::Test {};
+
+TEST_F(ABGeneratorTest, SplitSourceCopyTest) {
+  InstallOperation op;
+  op.set_type(InstallOperation::SOURCE_COPY);
+  *(op.add_src_extents()) = ExtentForRange(2, 3);
+  *(op.add_src_extents()) = ExtentForRange(6, 1);
+  *(op.add_src_extents()) = ExtentForRange(8, 4);
+  *(op.add_dst_extents()) = ExtentForRange(10, 2);
+  *(op.add_dst_extents()) = ExtentForRange(14, 3);
+  *(op.add_dst_extents()) = ExtentForRange(18, 3);
+
+  AnnotatedOperation aop;
+  aop.op = op;
+  aop.name = "SplitSourceCopyTestOp";
+  vector<AnnotatedOperation> result_ops;
+  EXPECT_TRUE(ABGenerator::SplitSourceCopy(aop, &result_ops));
+  EXPECT_EQ(result_ops.size(), 3);
+
+  EXPECT_EQ("SplitSourceCopyTestOp:0", result_ops[0].name);
+  InstallOperation first_op = result_ops[0].op;
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, first_op.type());
+  EXPECT_EQ(kBlockSize * 2, first_op.src_length());
+  EXPECT_EQ(1, first_op.src_extents().size());
+  EXPECT_EQ(2, first_op.src_extents(0).start_block());
+  EXPECT_EQ(2, first_op.src_extents(0).num_blocks());
+  EXPECT_EQ(kBlockSize * 2, first_op.dst_length());
+  EXPECT_EQ(1, first_op.dst_extents().size());
+  EXPECT_EQ(10, first_op.dst_extents(0).start_block());
+  EXPECT_EQ(2, first_op.dst_extents(0).num_blocks());
+
+  EXPECT_EQ("SplitSourceCopyTestOp:1", result_ops[1].name);
+  InstallOperation second_op = result_ops[1].op;
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, second_op.type());
+  EXPECT_EQ(kBlockSize * 3, second_op.src_length());
+  EXPECT_EQ(3, second_op.src_extents().size());
+  EXPECT_EQ(4, second_op.src_extents(0).start_block());
+  EXPECT_EQ(1, second_op.src_extents(0).num_blocks());
+  EXPECT_EQ(6, second_op.src_extents(1).start_block());
+  EXPECT_EQ(1, second_op.src_extents(1).num_blocks());
+  EXPECT_EQ(8, second_op.src_extents(2).start_block());
+  EXPECT_EQ(1, second_op.src_extents(2).num_blocks());
+  EXPECT_EQ(kBlockSize * 3, second_op.dst_length());
+  EXPECT_EQ(1, second_op.dst_extents().size());
+  EXPECT_EQ(14, second_op.dst_extents(0).start_block());
+  EXPECT_EQ(3, second_op.dst_extents(0).num_blocks());
+
+  EXPECT_EQ("SplitSourceCopyTestOp:2", result_ops[2].name);
+  InstallOperation third_op = result_ops[2].op;
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, third_op.type());
+  EXPECT_EQ(kBlockSize * 3, third_op.src_length());
+  EXPECT_EQ(1, third_op.src_extents().size());
+  EXPECT_EQ(9, third_op.src_extents(0).start_block());
+  EXPECT_EQ(3, third_op.src_extents(0).num_blocks());
+  EXPECT_EQ(kBlockSize * 3, third_op.dst_length());
+  EXPECT_EQ(1, third_op.dst_extents().size());
+  EXPECT_EQ(18, third_op.dst_extents(0).start_block());
+  EXPECT_EQ(3, third_op.dst_extents(0).num_blocks());
+}
+
+TEST_F(ABGeneratorTest, SplitReplaceTest) {
+  TestSplitReplaceOrReplaceBzOperation(InstallOperation::REPLACE, false);
+}
+
+TEST_F(ABGeneratorTest, SplitReplaceIntoReplaceBzTest) {
+  TestSplitReplaceOrReplaceBzOperation(InstallOperation::REPLACE, true);
+}
+
+TEST_F(ABGeneratorTest, SplitReplaceBzTest) {
+  TestSplitReplaceOrReplaceBzOperation(InstallOperation::REPLACE_BZ, true);
+}
+
+TEST_F(ABGeneratorTest, SplitReplaceBzIntoReplaceTest) {
+  TestSplitReplaceOrReplaceBzOperation(InstallOperation::REPLACE_BZ, false);
+}
+
+TEST_F(ABGeneratorTest, SortOperationsByDestinationTest) {
+  vector<AnnotatedOperation> aops;
+  // One operation with multiple destination extents.
+  InstallOperation first_op;
+  *(first_op.add_dst_extents()) = ExtentForRange(6, 1);
+  *(first_op.add_dst_extents()) = ExtentForRange(10, 2);
+  AnnotatedOperation first_aop;
+  first_aop.op = first_op;
+  first_aop.name = "first";
+  aops.push_back(first_aop);
+
+  // One with no destination extent. Should end up at the end of the vector.
+  InstallOperation second_op;
+  AnnotatedOperation second_aop;
+  second_aop.op = second_op;
+  second_aop.name = "second";
+  aops.push_back(second_aop);
+
+  // One with one destination extent.
+  InstallOperation third_op;
+  *(third_op.add_dst_extents()) = ExtentForRange(3, 2);
+  AnnotatedOperation third_aop;
+  third_aop.op = third_op;
+  third_aop.name = "third";
+  aops.push_back(third_aop);
+
+  ABGenerator::SortOperationsByDestination(&aops);
+  EXPECT_EQ(aops.size(), 3);
+  EXPECT_EQ(third_aop.name, aops[0].name);
+  EXPECT_EQ(first_aop.name, aops[1].name);
+  EXPECT_EQ(second_aop.name, aops[2].name);
+}
+
+TEST_F(ABGeneratorTest, MergeSourceCopyOperationsTest) {
+  vector<AnnotatedOperation> aops;
+  InstallOperation first_op;
+  first_op.set_type(InstallOperation::SOURCE_COPY);
+  first_op.set_src_length(kBlockSize);
+  first_op.set_dst_length(kBlockSize);
+  *(first_op.add_src_extents()) = ExtentForRange(1, 1);
+  *(first_op.add_dst_extents()) = ExtentForRange(6, 1);
+  AnnotatedOperation first_aop;
+  first_aop.op = first_op;
+  first_aop.name = "1";
+  aops.push_back(first_aop);
+
+  InstallOperation second_op;
+  second_op.set_type(InstallOperation::SOURCE_COPY);
+  second_op.set_src_length(3 * kBlockSize);
+  second_op.set_dst_length(3 * kBlockSize);
+  *(second_op.add_src_extents()) = ExtentForRange(2, 2);
+  *(second_op.add_src_extents()) = ExtentForRange(8, 2);
+  *(second_op.add_dst_extents()) = ExtentForRange(7, 3);
+  *(second_op.add_dst_extents()) = ExtentForRange(11, 1);
+  AnnotatedOperation second_aop;
+  second_aop.op = second_op;
+  second_aop.name = "2";
+  aops.push_back(second_aop);
+
+  InstallOperation third_op;
+  third_op.set_type(InstallOperation::SOURCE_COPY);
+  third_op.set_src_length(kBlockSize);
+  third_op.set_dst_length(kBlockSize);
+  *(third_op.add_src_extents()) = ExtentForRange(11, 1);
+  *(third_op.add_dst_extents()) = ExtentForRange(12, 1);
+  AnnotatedOperation third_aop;
+  third_aop.op = third_op;
+  third_aop.name = "3";
+  aops.push_back(third_aop);
+
+  BlobFileWriter blob_file(0, nullptr);
+  EXPECT_TRUE(ABGenerator::MergeOperations(&aops, 5, "", &blob_file));
+
+  EXPECT_EQ(aops.size(), 1);
+  InstallOperation first_result_op = aops[0].op;
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, first_result_op.type());
+  EXPECT_EQ(kBlockSize * 5, first_result_op.src_length());
+  EXPECT_EQ(3, first_result_op.src_extents().size());
+  EXPECT_TRUE(ExtentEquals(first_result_op.src_extents(0), 1, 3));
+  EXPECT_TRUE(ExtentEquals(first_result_op.src_extents(1), 8, 2));
+  EXPECT_TRUE(ExtentEquals(first_result_op.src_extents(2), 11, 1));
+  EXPECT_EQ(kBlockSize * 5, first_result_op.dst_length());
+  EXPECT_EQ(2, first_result_op.dst_extents().size());
+  EXPECT_TRUE(ExtentEquals(first_result_op.dst_extents(0), 6, 4));
+  EXPECT_TRUE(ExtentEquals(first_result_op.dst_extents(1), 11, 2));
+  EXPECT_EQ(aops[0].name, "1,2,3");
+}
+
+TEST_F(ABGeneratorTest, MergeReplaceOperationsTest) {
+  TestMergeReplaceOrReplaceBzOperations(InstallOperation::REPLACE, false);
+}
+
+TEST_F(ABGeneratorTest, MergeReplaceOperationsToReplaceBzTest) {
+  TestMergeReplaceOrReplaceBzOperations(InstallOperation::REPLACE, true);
+}
+
+TEST_F(ABGeneratorTest, MergeReplaceBzOperationsTest) {
+  TestMergeReplaceOrReplaceBzOperations(InstallOperation::REPLACE_BZ, true);
+}
+
+TEST_F(ABGeneratorTest, MergeReplaceBzOperationsToReplaceTest) {
+  TestMergeReplaceOrReplaceBzOperations(InstallOperation::REPLACE_BZ, false);
+}
+
+TEST_F(ABGeneratorTest, NoMergeOperationsTest) {
+  // Test to make sure we don't merge operations that shouldn't be merged.
+  vector<AnnotatedOperation> aops;
+  InstallOperation first_op;
+  first_op.set_type(InstallOperation::REPLACE_BZ);
+  *(first_op.add_dst_extents()) = ExtentForRange(0, 1);
+  first_op.set_data_length(kBlockSize);
+  AnnotatedOperation first_aop;
+  first_aop.op = first_op;
+  aops.push_back(first_aop);
+
+  // Should merge with first, except op types don't match...
+  InstallOperation second_op;
+  second_op.set_type(InstallOperation::REPLACE);
+  *(second_op.add_dst_extents()) = ExtentForRange(1, 2);
+  second_op.set_data_length(2 * kBlockSize);
+  AnnotatedOperation second_aop;
+  second_aop.op = second_op;
+  aops.push_back(second_aop);
+
+  // Should merge with second, except it would exceed chunk size...
+  InstallOperation third_op;
+  third_op.set_type(InstallOperation::REPLACE);
+  *(third_op.add_dst_extents()) = ExtentForRange(3, 3);
+  third_op.set_data_length(3 * kBlockSize);
+  AnnotatedOperation third_aop;
+  third_aop.op = third_op;
+  aops.push_back(third_aop);
+
+  // Should merge with third, except they aren't contiguous...
+  InstallOperation fourth_op;
+  fourth_op.set_type(InstallOperation::REPLACE);
+  *(fourth_op.add_dst_extents()) = ExtentForRange(7, 2);
+  fourth_op.set_data_length(2 * kBlockSize);
+  AnnotatedOperation fourth_aop;
+  fourth_aop.op = fourth_op;
+  aops.push_back(fourth_aop);
+
+  BlobFileWriter blob_file(0, nullptr);
+  EXPECT_TRUE(ABGenerator::MergeOperations(&aops, 4, "", &blob_file));
+
+  // No operations were merged, the number of ops is the same.
+  EXPECT_EQ(aops.size(), 4);
+}
+
+TEST_F(ABGeneratorTest, AddSourceHashTest) {
+  vector<AnnotatedOperation> aops;
+  InstallOperation first_op;
+  first_op.set_type(InstallOperation::SOURCE_COPY);
+  first_op.set_src_length(kBlockSize);
+  *(first_op.add_src_extents()) = ExtentForRange(0, 1);
+  AnnotatedOperation first_aop;
+  first_aop.op = first_op;
+  aops.push_back(first_aop);
+
+  InstallOperation second_op;
+  second_op.set_type(InstallOperation::REPLACE);
+  AnnotatedOperation second_aop;
+  second_aop.op = second_op;
+  aops.push_back(second_aop);
+
+  string src_part_path;
+  EXPECT_TRUE(utils::MakeTempFile("AddSourceHashTest_src_part.XXXXXX",
+                                  &src_part_path, nullptr));
+  ScopedPathUnlinker src_part_path_unlinker(src_part_path);
+  brillo::Blob src_data(kBlockSize);
+  test_utils::FillWithData(&src_data);
+  ASSERT_TRUE(utils::WriteFile(src_part_path.c_str(), src_data.data(),
+                               src_data.size()));
+
+  EXPECT_TRUE(ABGenerator::AddSourceHash(&aops, src_part_path));
+
+  EXPECT_TRUE(aops[0].op.has_src_sha256_hash());
+  EXPECT_FALSE(aops[1].op.has_src_sha256_hash());
+  brillo::Blob expected_hash;
+  EXPECT_TRUE(HashCalculator::RawHashOfData(src_data, &expected_hash));
+  brillo::Blob result_hash(aops[0].op.src_sha256_hash().begin(),
+                           aops[0].op.src_sha256_hash().end());
+  EXPECT_EQ(expected_hash, result_hash);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/annotated_operation.cc b/payload_generator/annotated_operation.cc
new file mode 100644
index 0000000..984f921
--- /dev/null
+++ b/payload_generator/annotated_operation.cc
@@ -0,0 +1,70 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/annotated_operation.h"
+
+#include <base/format_macros.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+
+namespace chromeos_update_engine {
+
+namespace {
+// Output the list of extents as (start_block, num_blocks) in the passed output
+// stream.
+void OutputExtents(std::ostream* os,
+                   const google::protobuf::RepeatedPtrField<Extent>& extents) {
+  for (const auto& extent : extents) {
+    *os << " (" << extent.start_block() << ", " << extent.num_blocks() << ")";
+  }
+}
+}  // namespace
+
+bool AnnotatedOperation::SetOperationBlob(brillo::Blob* blob,
+                                          BlobFileWriter* blob_file) {
+  off_t data_offset = blob_file->StoreBlob(*blob);
+  TEST_AND_RETURN_FALSE(data_offset != -1);
+  op.set_data_offset(data_offset);
+  op.set_data_length(blob->size());
+  return true;
+}
+
+std::ostream& operator<<(std::ostream& os, const AnnotatedOperation& aop) {
+  // For example, this prints:
+  // REPLACE_BZ 500 @3000
+  //   name: /foo/bar
+  //    dst: (123, 3) (127, 2)
+  os << InstallOperationTypeName(aop.op.type()) << " "  << aop.op.data_length();
+  if (aop.op.data_length() > 0)
+    os << " @" << aop.op.data_offset();
+  if (!aop.name.empty()) {
+    os << std::endl << "  name: " << aop.name;
+  }
+  if (aop.op.src_extents_size() != 0) {
+    os << std::endl << "   src:";
+    OutputExtents(&os, aop.op.src_extents());
+  }
+  if (aop.op.dst_extents_size() != 0) {
+    os << std::endl << "   dst:";
+    OutputExtents(&os, aop.op.dst_extents());
+  }
+  return os;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/annotated_operation.h b/payload_generator/annotated_operation.h
new file mode 100644
index 0000000..4076070
--- /dev/null
+++ b/payload_generator/annotated_operation.h
@@ -0,0 +1,49 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_ANNOTATED_OPERATION_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_ANNOTATED_OPERATION_H_
+
+#include <ostream>  // NOLINT(readability/streams)
+#include <string>
+
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+struct AnnotatedOperation {
+  // The name given to the operation, for logging and debugging purposes only.
+  // This normally includes the path to the file and the chunk used, if any.
+  std::string name;
+
+  // The InstallOperation, as defined by the protobuf.
+  InstallOperation op;
+
+  // Writes |blob| to the end of |data_fd|, and updates |data_file_size| to
+  // match the new size of |data_fd|. It sets the data_offset and data_length
+  // in AnnotatedOperation to match the offset and size of |blob| in |data_fd|.
+  bool SetOperationBlob(brillo::Blob* blob, BlobFileWriter* blob_file);
+};
+
+// For logging purposes.
+std::ostream& operator<<(std::ostream& os, const AnnotatedOperation& aop);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_ANNOTATED_OPERATION_H_
diff --git a/payload_generator/blob_file_writer.cc b/payload_generator/blob_file_writer.cc
new file mode 100644
index 0000000..8225df4
--- /dev/null
+++ b/payload_generator/blob_file_writer.cc
@@ -0,0 +1,47 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/blob_file_writer.h"
+
+#include "update_engine/common/utils.h"
+
+namespace chromeos_update_engine {
+
+off_t BlobFileWriter::StoreBlob(const brillo::Blob& blob) {
+  base::AutoLock auto_lock(blob_mutex_);
+  if (!utils::PWriteAll(blob_fd_, blob.data(), blob.size(), *blob_file_size_))
+    return -1;
+
+  off_t result = *blob_file_size_;
+  *blob_file_size_ += blob.size();
+
+  stored_blobs_++;
+  if (total_blobs_ > 0 &&
+      (10 * (stored_blobs_ - 1) / total_blobs_) !=
+      (10 * stored_blobs_ / total_blobs_)) {
+    LOG(INFO) << (100 * stored_blobs_ / total_blobs_)
+              << "% complete " << stored_blobs_ << "/" << total_blobs_
+              << " ops (output size: " << *blob_file_size_ << ")";
+  }
+  return result;
+}
+
+void BlobFileWriter::SetTotalBlobs(size_t total_blobs) {
+  total_blobs_ = total_blobs;
+  stored_blobs_ = 0;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/blob_file_writer.h b/payload_generator/blob_file_writer.h
new file mode 100644
index 0000000..cbc13ae
--- /dev/null
+++ b/payload_generator/blob_file_writer.h
@@ -0,0 +1,59 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOB_FILE_WRITER_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOB_FILE_WRITER_H_
+
+#include <base/macros.h>
+
+#include <base/synchronization/lock.h>
+#include <brillo/secure_blob.h>
+
+namespace chromeos_update_engine {
+
+class BlobFileWriter {
+ public:
+  // Create the BlobFileWriter object that will manage the blobs stored to
+  // |blob_fd| in a thread safe way.
+  BlobFileWriter(int blob_fd, off_t* blob_file_size)
+    : blob_fd_(blob_fd),
+      blob_file_size_(blob_file_size) {}
+
+  // Store the passed |blob| in the blob file. Returns the offset at which it
+  // was stored, or -1 in case of failure.
+  off_t StoreBlob(const brillo::Blob& blob);
+
+  // The number of |total_blobs| is the number of blobs that will be stored but
+  // is only used for logging purposes. If not set or set to 0, logging will be
+  // skipped. This function will also reset the number of stored blobs to 0.
+  void SetTotalBlobs(size_t total_blobs);
+
+ private:
+  size_t total_blobs_{0};
+  size_t stored_blobs_{0};
+
+  // The file and its size are protected with the |blob_mutex_|.
+  int blob_fd_;
+  off_t* blob_file_size_;
+
+  base::Lock blob_mutex_;
+
+  DISALLOW_COPY_AND_ASSIGN(BlobFileWriter);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOB_FILE_WRITER_H_
diff --git a/payload_generator/blob_file_writer_unittest.cc b/payload_generator/blob_file_writer_unittest.cc
new file mode 100644
index 0000000..5f94ef3
--- /dev/null
+++ b/payload_generator/blob_file_writer_unittest.cc
@@ -0,0 +1,59 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/blob_file_writer.h"
+
+#include <string>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using chromeos_update_engine::test_utils::FillWithData;
+using std::string;
+
+namespace chromeos_update_engine {
+
+class BlobFileWriterTest : public ::testing::Test {};
+
+TEST(BlobFileWriterTest, SimpleTest) {
+  string blob_path;
+  int blob_fd;
+  EXPECT_TRUE(utils::MakeTempFile("BlobFileWriterTest.XXXXXX",
+                                  &blob_path,
+                                  &blob_fd));
+  off_t blob_file_size = 0;
+  BlobFileWriter blob_file(blob_fd, &blob_file_size);
+
+  off_t blob_size = 1024;
+  brillo::Blob blob(blob_size);
+  FillWithData(&blob);
+  EXPECT_EQ(0, blob_file.StoreBlob(blob));
+  EXPECT_EQ(blob_size, blob_file.StoreBlob(blob));
+
+  brillo::Blob stored_blob(blob_size);
+  ssize_t bytes_read;
+  ASSERT_TRUE(utils::PReadAll(blob_fd,
+                              stored_blob.data(),
+                              blob_size,
+                              0,
+                              &bytes_read));
+  EXPECT_EQ(bytes_read, blob_size);
+  EXPECT_EQ(blob, stored_blob);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/block_mapping.cc b/payload_generator/block_mapping.cc
new file mode 100644
index 0000000..ff10f0b
--- /dev/null
+++ b/payload_generator/block_mapping.cc
@@ -0,0 +1,161 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/block_mapping.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <functional>
+#include <string>
+#include <vector>
+
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace {
+
+size_t HashValue(const brillo::Blob& blob) {
+  std::hash<string> hash_fn;
+  return hash_fn(string(blob.begin(), blob.end()));
+}
+
+}  // namespace
+
+namespace chromeos_update_engine {
+
+BlockMapping::BlockId BlockMapping::AddBlock(const brillo::Blob& block_data) {
+  return AddBlock(-1, 0, block_data);
+}
+
+BlockMapping::BlockId BlockMapping::AddDiskBlock(int fd, off_t byte_offset) {
+  brillo::Blob blob(block_size_);
+  ssize_t bytes_read = 0;
+  if (!utils::PReadAll(fd, blob.data(), block_size_, byte_offset, &bytes_read))
+    return -1;
+  if (static_cast<size_t>(bytes_read) != block_size_)
+    return -1;
+  return AddBlock(fd, byte_offset, blob);
+}
+
+bool BlockMapping::AddManyDiskBlocks(int fd,
+                                     off_t initial_byte_offset,
+                                     size_t num_blocks,
+                                     vector<BlockId>* block_ids) {
+  bool ret = true;
+  block_ids->resize(num_blocks);
+  for (size_t block = 0; block < num_blocks; block++) {
+    (*block_ids)[block] = AddDiskBlock(
+        fd, initial_byte_offset + block * block_size_);
+    ret = ret && (*block_ids)[block] != -1;
+  }
+  return ret;
+}
+
+BlockMapping::BlockId BlockMapping::AddBlock(int fd,
+                                             off_t byte_offset,
+                                             const brillo::Blob& block_data) {
+  if (block_data.size() != block_size_)
+    return -1;
+  size_t h = HashValue(block_data);
+
+  // We either reuse a UniqueBlock or create a new one. If we need a new
+  // UniqueBlock it could also be part of a new or existing bucket (if there is
+  // a hash collision).
+  vector<UniqueBlock> *bucket = nullptr;
+
+  auto mapping_it = mapping_.find(h);
+  if (mapping_it == mapping_.end()) {
+    bucket = &mapping_[h];
+  } else {
+    for (UniqueBlock& existing_block : mapping_it->second) {
+      bool equals = false;
+      if (!existing_block.CompareData(block_data, &equals))
+        return -1;
+      if (equals)
+        return existing_block.block_id;
+    }
+    bucket = &mapping_it->second;
+  }
+
+  // No existing block was found at this point, so we create and fill in a new
+  // one.
+  bucket->emplace_back();
+  UniqueBlock *new_ublock = &bucket->back();
+
+  new_ublock->times_read = 1;
+  new_ublock->fd = fd;
+  new_ublock->byte_offset = byte_offset;
+  new_ublock->block_id = used_block_ids++;
+  // We need to cache blocks that are not referencing any disk location.
+  if (fd == -1)
+    new_ublock->block_data = block_data;
+
+  return new_ublock->block_id;
+}
+
+bool BlockMapping::UniqueBlock::CompareData(const brillo::Blob& other_block,
+                                            bool* equals) {
+  if (!block_data.empty()) {
+    *equals = block_data == other_block;
+    return true;
+  }
+  const size_t block_size = other_block.size();
+  brillo::Blob blob(block_size);
+  ssize_t bytes_read = 0;
+  if (!utils::PReadAll(fd, blob.data(), block_size, byte_offset, &bytes_read))
+    return false;
+  if (static_cast<size_t>(bytes_read) != block_size)
+    return false;
+  *equals = blob == other_block;
+
+  // We increase the number of times we had to read this block from disk and
+  // we cache this block based on that. This caching method is optimized for
+  // the common use case of having two partitions that share blocks between them
+  // but have few repeated blocks inside each partition, such as the block
+  // with all zeros or duplicated files.
+  times_read++;
+  if (times_read > 3)
+    block_data = std::move(blob);
+  return true;
+}
+
+bool MapPartitionBlocks(const string& old_part,
+                        const string& new_part,
+                        size_t old_size,
+                        size_t new_size,
+                        size_t block_size,
+                        vector<BlockMapping::BlockId>* old_block_ids,
+                        vector<BlockMapping::BlockId>* new_block_ids) {
+  BlockMapping mapping(block_size);
+  if (mapping.AddBlock(brillo::Blob(block_size, '\0')) != 0)
+    return false;
+  int old_fd = HANDLE_EINTR(open(old_part.c_str(), O_RDONLY));
+  int new_fd = HANDLE_EINTR(open(new_part.c_str(), O_RDONLY));
+  ScopedFdCloser old_fd_closer(&old_fd);
+  ScopedFdCloser new_fd_closer(&new_fd);
+
+  TEST_AND_RETURN_FALSE(mapping.AddManyDiskBlocks(
+      old_fd, 0, old_size / block_size, old_block_ids));
+  TEST_AND_RETURN_FALSE(mapping.AddManyDiskBlocks(
+      new_fd, 0, new_size / block_size, new_block_ids));
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/block_mapping.h b/payload_generator/block_mapping.h
new file mode 100644
index 0000000..3fe94ab
--- /dev/null
+++ b/payload_generator/block_mapping.h
@@ -0,0 +1,112 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOCK_MAPPING_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOCK_MAPPING_H_
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/payload_generator/payload_generation_config.h"
+
+namespace chromeos_update_engine {
+
+// BlockMapping allows to map data blocks (brillo::Blobs of block_size size)
+// into unique integer values called "block ids". This mapping differs from a
+// hash function in that two blocks with the same data will have the same id but
+// also two blocks with the same id will have the same data. This is only valid
+// in the context of the same BlockMapping instance.
+class BlockMapping {
+ public:
+  using BlockId = int64_t;
+
+  explicit BlockMapping(size_t block_size) : block_size_(block_size) {}
+
+  // Add a single data block to the mapping. Returns its unique block id.
+  // In case of error returns -1.
+  BlockId AddBlock(const brillo::Blob& block_data);
+
+  // Add a block from disk reading it from the file descriptor |fd| from the
+  // offset in bytes |byte_offset|. The data block may or may not be cached, so
+  // the file descriptor must be available until the BlockMapping is destroyed.
+  // Returns the unique block id of the added block or -1 in case of error.
+  BlockId AddDiskBlock(int fd, off_t byte_offset);
+
+  // This is a helper method to add |num_blocks| contiguous blocks reading them
+  // from the file descriptor |fd| starting at offset |initial_byte_offset|.
+  // Returns whether it succeeded to add all the disk blocks and stores in
+  // |block_ids| the block id for each one of the added blocks.
+  bool AddManyDiskBlocks(int fd, off_t initial_byte_offset, size_t num_blocks,
+                         std::vector<BlockId>* block_ids);
+
+ private:
+  FRIEND_TEST(BlockMappingTest, BlocksAreNotKeptInMemory);
+
+  // Add a single block passed in |block_data|. If |fd| is not -1, the block
+  // can be discarded to save RAM and retrieved later from |fd| at the position
+  // |byte_offset|.
+  BlockId AddBlock(int fd, off_t byte_offset, const brillo::Blob& block_data);
+
+  size_t block_size_;
+
+  BlockId used_block_ids{0};
+
+  // The UniqueBlock represents the data of a block associated to a unique
+  // block id.
+  struct UniqueBlock {
+    brillo::Blob block_data;
+
+    // The block id assigned to this unique block.
+    BlockId block_id;
+
+    // The location on this unique block on disk (if not cached in block_data).
+    int fd{-1};
+    off_t byte_offset{0};
+
+    // Number of times we have seen this data block. Used for caching.
+    uint32_t times_read{0};
+
+    // Compares the UniqueBlock data with the other_block data and stores if
+    // they are equal in |equals|. Returns whether there was an error reading
+    // the block from disk while comparing it.
+    bool CompareData(const brillo::Blob& other_block, bool* equals);
+  };
+
+  // A mapping from hash values to possible block ids.
+  std::map<size_t, std::vector<UniqueBlock>> mapping_;
+};
+
+// Maps the blocks of the old and new partitions |old_part| and |new_part| whose
+// size in bytes are |old_size| and |new_size| into block ids where two blocks
+// with the same data will have the same block id and vice versa, regardless of
+// the partition they are on.
+// The block ids number 0 corresponds to the block with all zeros, but any
+// other block id number is assigned randomly.
+bool MapPartitionBlocks(const std::string& old_part,
+                        const std::string& new_part,
+                        size_t old_size,
+                        size_t new_size,
+                        size_t block_size,
+                        std::vector<BlockMapping::BlockId>* old_block_ids,
+                        std::vector<BlockMapping::BlockId>* new_block_ids);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_BLOCK_MAPPING_H_
diff --git a/payload_generator/block_mapping_unittest.cc b/payload_generator/block_mapping_unittest.cc
new file mode 100644
index 0000000..18e48c4
--- /dev/null
+++ b/payload_generator/block_mapping_unittest.cc
@@ -0,0 +1,134 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/block_mapping.h"
+
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <string>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+}  // namespace
+
+class BlockMappingTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    EXPECT_TRUE(utils::MakeTempFile("BlockMappingTest_old.XXXXXX",
+                                    &old_part_path_,
+                                    nullptr));
+    EXPECT_TRUE(utils::MakeTempFile("BlockMappingTest_new.XXXXXX",
+                                    &new_part_path_,
+                                    nullptr));
+
+    old_part_unlinker_.reset(new ScopedPathUnlinker(old_part_path_));
+    new_part_unlinker_.reset(new ScopedPathUnlinker(new_part_path_));
+  }
+
+  // Old new partition files used in testing.
+  string old_part_path_;
+  string new_part_path_;
+  std::unique_ptr<ScopedPathUnlinker> old_part_unlinker_;
+  std::unique_ptr<ScopedPathUnlinker> new_part_unlinker_;
+
+  size_t block_size_{1024};
+  BlockMapping bm_{block_size_};  // BlockMapping under test.
+};
+
+TEST_F(BlockMappingTest, FirstAddedBlockIsZero) {
+  brillo::Blob blob(block_size_);
+  // The BlockMapping just assigns the block ids in order, so it doesn't matter
+  // what are the contents of the first block.
+  blob[0] = 42;
+  EXPECT_EQ(0, bm_.AddBlock(blob));
+  blob[0] = 5;
+  EXPECT_EQ(1, bm_.AddBlock(blob));
+}
+
+TEST_F(BlockMappingTest, BlocksAreNotKeptInMemory) {
+  test_utils::WriteFileString(old_part_path_, string(block_size_, 'a'));
+  int old_fd = HANDLE_EINTR(open(old_part_path_.c_str(), O_RDONLY));
+  ScopedFdCloser old_fd_closer(&old_fd);
+
+  EXPECT_EQ(0, bm_.AddDiskBlock(old_fd, 0));
+
+  // Check that the block_data is not stored on memory if we just used the block
+  // once.
+  for (const auto& it : bm_.mapping_) {
+    for (const BlockMapping::UniqueBlock& ublock : it.second) {
+      EXPECT_TRUE(ublock.block_data.empty());
+    }
+  }
+
+  brillo::Blob block(block_size_, 'a');
+  for (int i = 0; i < 5; ++i) {
+    // Re-add the same block 5 times.
+    EXPECT_EQ(0, bm_.AddBlock(block));
+  }
+
+  for (const auto& it : bm_.mapping_) {
+    for (const BlockMapping::UniqueBlock& ublock : it.second) {
+      EXPECT_FALSE(ublock.block_data.empty());
+      // The block was loaded from disk only 4 times, and after that the counter
+      // is not updated anymore.
+      EXPECT_EQ(4, ublock.times_read);
+    }
+  }
+}
+
+TEST_F(BlockMappingTest, MapPartitionBlocks) {
+  // A string with 10 blocks where all the blocks are different.
+  string old_contents(10 * block_size_, '\0');
+  for (size_t i = 0; i < old_contents.size(); ++i)
+    old_contents[i] = 4 + i / block_size_;
+  test_utils::WriteFileString(old_part_path_, old_contents);
+
+  // A string including the block with all zeros and overlapping some of the
+  // other blocks in old_contents.
+  string new_contents(6 * block_size_, '\0');
+  for (size_t i = 0; i < new_contents.size(); ++i)
+    new_contents[i] = i / block_size_;
+  test_utils::WriteFileString(new_part_path_, new_contents);
+
+  vector<BlockMapping::BlockId> old_ids, new_ids;
+  EXPECT_TRUE(MapPartitionBlocks(old_part_path_,
+                                 new_part_path_,
+                                 old_contents.size(),
+                                 new_contents.size(),
+                                 block_size_,
+                                 &old_ids,
+                                 &new_ids));
+
+  EXPECT_EQ((vector<BlockMapping::BlockId>{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}),
+            old_ids);
+  EXPECT_EQ((vector<BlockMapping::BlockId>{0, 11, 12, 13, 1, 2}),
+            new_ids);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/bzip.cc b/payload_generator/bzip.cc
new file mode 100644
index 0000000..9040193
--- /dev/null
+++ b/payload_generator/bzip.cc
@@ -0,0 +1,130 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/bzip.h"
+
+#include <bzlib.h>
+#include <stdlib.h>
+
+#include <algorithm>
+#include <limits>
+
+#include "update_engine/common/utils.h"
+
+using std::string;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// BzipData compresses or decompresses the input to the output.
+// Returns true on success.
+// Use one of BzipBuffToBuff*ompress as the template parameter to BzipData().
+int BzipBuffToBuffDecompress(uint8_t* out,
+                             uint32_t* out_length,
+                             const void* in,
+                             uint32_t in_length) {
+  return BZ2_bzBuffToBuffDecompress(
+      reinterpret_cast<char*>(out),
+      out_length,
+      reinterpret_cast<char*>(const_cast<void*>(in)),
+      in_length,
+      0,  // Silent verbosity
+      0);  // Normal algorithm
+}
+
+int BzipBuffToBuffCompress(uint8_t* out,
+                           uint32_t* out_length,
+                           const void* in,
+                           uint32_t in_length) {
+  return BZ2_bzBuffToBuffCompress(
+      reinterpret_cast<char*>(out),
+      out_length,
+      reinterpret_cast<char*>(const_cast<void*>(in)),
+      in_length,
+      9,  // Best compression
+      0,  // Silent verbosity
+      0);  // Default work factor
+}
+
+template<int F(uint8_t* out,
+               uint32_t* out_length,
+               const void* in,
+               uint32_t in_length)>
+bool BzipData(const void* const in,
+              const size_t in_size,
+              brillo::Blob* const out) {
+  TEST_AND_RETURN_FALSE(out);
+  out->clear();
+  if (in_size == 0) {
+    return true;
+  }
+  // Try increasing buffer size until it works
+  size_t buf_size = in_size;
+  out->resize(buf_size);
+
+  for (;;) {
+    if (buf_size > std::numeric_limits<uint32_t>::max())
+      return false;
+    uint32_t data_size = buf_size;
+    int rc = F(out->data(), &data_size, in, in_size);
+    TEST_AND_RETURN_FALSE(rc == BZ_OUTBUFF_FULL || rc == BZ_OK);
+    if (rc == BZ_OK) {
+      // we're done!
+      out->resize(data_size);
+      return true;
+    }
+
+    // Data didn't fit; double the buffer size.
+    buf_size *= 2;
+    out->resize(buf_size);
+  }
+}
+
+}  // namespace
+
+bool BzipDecompress(const brillo::Blob& in, brillo::Blob* out) {
+  return BzipData<BzipBuffToBuffDecompress>(in.data(), in.size(), out);
+}
+
+bool BzipCompress(const brillo::Blob& in, brillo::Blob* out) {
+  return BzipData<BzipBuffToBuffCompress>(in.data(), in.size(), out);
+}
+
+namespace {
+template<bool F(const void* const in,
+                const size_t in_size,
+                brillo::Blob* const out)>
+bool BzipString(const string& str,
+                brillo::Blob* out) {
+  TEST_AND_RETURN_FALSE(out);
+  brillo::Blob temp;
+  TEST_AND_RETURN_FALSE(F(str.data(), str.size(), &temp));
+  out->clear();
+  out->insert(out->end(), temp.begin(), temp.end());
+  return true;
+}
+}  // namespace
+
+bool BzipCompressString(const string& str, brillo::Blob* out) {
+  return BzipString<BzipData<BzipBuffToBuffCompress>>(str, out);
+}
+
+bool BzipDecompressString(const string& str, brillo::Blob* out) {
+  return BzipString<BzipData<BzipBuffToBuffDecompress>>(str, out);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/bzip.h b/payload_generator/bzip.h
new file mode 100644
index 0000000..ca9956e
--- /dev/null
+++ b/payload_generator/bzip.h
@@ -0,0 +1,35 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_BZIP_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_BZIP_H_
+
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+
+namespace chromeos_update_engine {
+
+// Bzip2 compresses or decompresses str/in to out.
+bool BzipDecompress(const brillo::Blob& in, brillo::Blob* out);
+bool BzipCompress(const brillo::Blob& in, brillo::Blob* out);
+bool BzipCompressString(const std::string& str, brillo::Blob* out);
+bool BzipDecompressString(const std::string& str, brillo::Blob* out);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_BZIP_H_
diff --git a/payload_generator/cycle_breaker.cc b/payload_generator/cycle_breaker.cc
new file mode 100644
index 0000000..321732e
--- /dev/null
+++ b/payload_generator/cycle_breaker.cc
@@ -0,0 +1,211 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_generator/cycle_breaker.h"
+
+#include <inttypes.h>
+
+#include <set>
+#include <string>
+#include <utility>
+
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/graph_utils.h"
+#include "update_engine/payload_generator/tarjan.h"
+
+using std::make_pair;
+using std::set;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+// This is the outer function from the original paper.
+void CycleBreaker::BreakCycles(const Graph& graph, set<Edge>* out_cut_edges) {
+  cut_edges_.clear();
+
+  // Make a copy, which we will modify by removing edges. Thus, in each
+  // iteration subgraph_ is the current subgraph or the original with
+  // vertices we desire. This variable was "A_K" in the original paper.
+  subgraph_ = graph;
+
+  // The paper calls for the "adjacency structure (i.e., graph) of
+  // strong (-ly connected) component K with least vertex in subgraph
+  // induced by {s, s + 1, ..., n}".
+  // We arbitrarily order each vertex by its index in the graph. Thus,
+  // each iteration, we are looking at the subgraph {s, s + 1, ..., n}
+  // and looking for the strongly connected component with vertex s.
+
+  TarjanAlgorithm tarjan;
+  skipped_ops_ = 0;
+
+  for (Graph::size_type i = 0; i < subgraph_.size(); i++) {
+    InstallOperation_Type op_type = graph[i].aop.op.type();
+    if (op_type == InstallOperation::REPLACE ||
+        op_type == InstallOperation::REPLACE_BZ) {
+      skipped_ops_++;
+      continue;
+    }
+
+    if (i > 0) {
+      // Erase node (i - 1) from subgraph_. First, erase what it points to
+      subgraph_[i - 1].out_edges.clear();
+      // Now, erase any pointers to node (i - 1)
+      for (Graph::size_type j = i; j < subgraph_.size(); j++) {
+        subgraph_[j].out_edges.erase(i - 1);
+      }
+    }
+
+    // Calculate SCC (strongly connected component) with vertex i.
+    vector<Vertex::Index> component_indexes;
+    tarjan.Execute(i, &subgraph_, &component_indexes);
+
+    // Set subgraph edges for the components in the SCC.
+    for (vector<Vertex::Index>::iterator it = component_indexes.begin();
+         it != component_indexes.end(); ++it) {
+      subgraph_[*it].subgraph_edges.clear();
+      for (vector<Vertex::Index>::iterator jt = component_indexes.begin();
+           jt != component_indexes.end(); ++jt) {
+        // If there's a link from *it -> *jt in the graph,
+        // add a subgraph_ edge
+        if (utils::MapContainsKey(subgraph_[*it].out_edges, *jt))
+          subgraph_[*it].subgraph_edges.insert(*jt);
+      }
+    }
+
+    current_vertex_ = i;
+    blocked_.clear();
+    blocked_.resize(subgraph_.size());
+    blocked_graph_.clear();
+    blocked_graph_.resize(subgraph_.size());
+    Circuit(current_vertex_, 0);
+  }
+
+  out_cut_edges->swap(cut_edges_);
+  LOG(INFO) << "Cycle breaker skipped " << skipped_ops_ << " ops.";
+  DCHECK(stack_.empty());
+}
+
+static const size_t kMaxEdgesToConsider = 2;
+
+void CycleBreaker::HandleCircuit() {
+  stack_.push_back(current_vertex_);
+  CHECK_GE(stack_.size(),
+           static_cast<vector<Vertex::Index>::size_type>(2));
+  Edge min_edge = make_pair(stack_[0], stack_[1]);
+  uint64_t min_edge_weight = kuint64max;
+  size_t edges_considered = 0;
+  for (vector<Vertex::Index>::const_iterator it = stack_.begin();
+       it != (stack_.end() - 1); ++it) {
+    Edge edge = make_pair(*it, *(it + 1));
+    if (cut_edges_.find(edge) != cut_edges_.end()) {
+      stack_.pop_back();
+      return;
+    }
+    uint64_t edge_weight = graph_utils::EdgeWeight(subgraph_, edge);
+    if (edge_weight < min_edge_weight) {
+      min_edge_weight = edge_weight;
+      min_edge = edge;
+    }
+    edges_considered++;
+    if (edges_considered == kMaxEdgesToConsider)
+      break;
+  }
+  cut_edges_.insert(min_edge);
+  stack_.pop_back();
+}
+
+void CycleBreaker::Unblock(Vertex::Index u) {
+  blocked_[u] = false;
+
+  for (Vertex::EdgeMap::iterator it = blocked_graph_[u].out_edges.begin();
+       it != blocked_graph_[u].out_edges.end(); ) {
+    Vertex::Index w = it->first;
+    blocked_graph_[u].out_edges.erase(it++);
+    if (blocked_[w])
+      Unblock(w);
+  }
+}
+
+bool CycleBreaker::StackContainsCutEdge() const {
+  for (vector<Vertex::Index>::const_iterator it = ++stack_.begin(),
+           e = stack_.end(); it != e; ++it) {
+    Edge edge = make_pair(*(it - 1), *it);
+    if (utils::SetContainsKey(cut_edges_, edge)) {
+      return true;
+    }
+  }
+  return false;
+}
+
+bool CycleBreaker::Circuit(Vertex::Index vertex, Vertex::Index depth) {
+  // "vertex" was "v" in the original paper.
+  bool found = false;  // Was "f" in the original paper.
+  stack_.push_back(vertex);
+  blocked_[vertex] = true;
+  {
+    static int counter = 0;
+    counter++;
+    if (counter == 10000) {
+      counter = 0;
+      std::string stack_str;
+      for (Vertex::Index index : stack_) {
+        stack_str += std::to_string(index);
+        stack_str += " -> ";
+      }
+      LOG(INFO) << "stack: " << stack_str;
+    }
+  }
+
+  for (Vertex::SubgraphEdgeMap::iterator w =
+           subgraph_[vertex].subgraph_edges.begin();
+       w != subgraph_[vertex].subgraph_edges.end(); ++w) {
+    if (*w == current_vertex_) {
+      // The original paper called for printing stack_ followed by
+      // current_vertex_ here, which is a cycle. Instead, we call
+      // HandleCircuit() to break it.
+      HandleCircuit();
+      found = true;
+    } else if (!blocked_[*w]) {
+      if (Circuit(*w, depth + 1)) {
+        found = true;
+        if ((depth > kMaxEdgesToConsider) || StackContainsCutEdge())
+          break;
+      }
+    }
+  }
+
+  if (found) {
+    Unblock(vertex);
+  } else {
+    for (Vertex::SubgraphEdgeMap::iterator w =
+             subgraph_[vertex].subgraph_edges.begin();
+         w != subgraph_[vertex].subgraph_edges.end(); ++w) {
+      if (blocked_graph_[*w].out_edges.find(vertex) ==
+          blocked_graph_[*w].out_edges.end()) {
+        blocked_graph_[*w].out_edges.insert(make_pair(vertex,
+                                                      EdgeProperties()));
+      }
+    }
+  }
+  CHECK_EQ(vertex, stack_.back());
+  stack_.pop_back();
+  return found;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/cycle_breaker.h b/payload_generator/cycle_breaker.h
new file mode 100644
index 0000000..231d63a
--- /dev/null
+++ b/payload_generator/cycle_breaker.h
@@ -0,0 +1,71 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_CYCLE_BREAKER_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_CYCLE_BREAKER_H_
+
+// This is a modified implementation of Donald B. Johnson's algorithm for
+// finding all elementary cycles (a.k.a. circuits) in a directed graph.
+// See the paper "Finding All the Elementary Circuits of a Directed Graph"
+// at http://dutta.csc.ncsu.edu/csc791_spring07/wrap/circuits_johnson.pdf
+// for reference.
+
+// Note: this version of the algorithm not only finds cycles, but breaks them.
+// It uses a simple greedy algorithm for cutting: when a cycle is discovered,
+// the edge with the least weight is cut. Longer term we may wish to do
+// something more intelligent, since the goal is (ideally) to minimize the
+// sum of the weights of all cut cycles. In practice, it's intractable
+// to consider all cycles before cutting any; there are simply too many.
+// In a sample graph representative of a typical workload, I found over
+// 5 * 10^15 cycles.
+
+#include <set>
+#include <vector>
+
+#include "update_engine/payload_generator/graph_types.h"
+
+namespace chromeos_update_engine {
+
+class CycleBreaker {
+ public:
+  CycleBreaker() : skipped_ops_(0) {}
+  // out_cut_edges is replaced with the cut edges.
+  void BreakCycles(const Graph& graph, std::set<Edge>* out_cut_edges);
+
+  size_t skipped_ops() const { return skipped_ops_; }
+
+ private:
+  void HandleCircuit();
+  void Unblock(Vertex::Index u);
+  bool Circuit(Vertex::Index vertex, Vertex::Index depth);
+  bool StackContainsCutEdge() const;
+
+  std::vector<bool> blocked_;  // "blocked" in the paper
+  Vertex::Index current_vertex_;  // "s" in the paper
+  std::vector<Vertex::Index> stack_;  // the stack variable in the paper
+  Graph subgraph_;  // "A_K" in the paper
+  Graph blocked_graph_;  // "B" in the paper
+
+  std::set<Edge> cut_edges_;
+
+  // Number of operations skipped b/c we know they don't have any
+  // incoming edges.
+  size_t skipped_ops_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_CYCLE_BREAKER_H_
diff --git a/payload_generator/cycle_breaker_unittest.cc b/payload_generator/cycle_breaker_unittest.cc
new file mode 100644
index 0000000..4053cf3
--- /dev/null
+++ b/payload_generator/cycle_breaker_unittest.cc
@@ -0,0 +1,278 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/cycle_breaker.h"
+
+#include <set>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/logging.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/graph_types.h"
+
+using std::make_pair;
+using std::pair;
+using std::set;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+void SetOpForNodes(Graph* graph) {
+  for (Vertex& vertex : *graph) {
+    vertex.aop.op.set_type(InstallOperation::MOVE);
+  }
+}
+}  // namespace
+
+class CycleBreakerTest : public ::testing::Test {};
+
+TEST(CycleBreakerTest, SimpleTest) {
+  int counter = 0;
+  const Vertex::Index n_a = counter++;
+  const Vertex::Index n_b = counter++;
+  const Vertex::Index n_c = counter++;
+  const Vertex::Index n_d = counter++;
+  const Vertex::Index n_e = counter++;
+  const Vertex::Index n_f = counter++;
+  const Vertex::Index n_g = counter++;
+  const Vertex::Index n_h = counter++;
+  const Graph::size_type kNodeCount = counter++;
+
+  Graph graph(kNodeCount);
+  SetOpForNodes(&graph);
+
+  graph[n_a].out_edges.insert(make_pair(n_e, EdgeProperties()));
+  graph[n_a].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_b].out_edges.insert(make_pair(n_a, EdgeProperties()));
+  graph[n_c].out_edges.insert(make_pair(n_d, EdgeProperties()));
+  graph[n_d].out_edges.insert(make_pair(n_e, EdgeProperties()));
+  graph[n_d].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_b, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_c, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_f].out_edges.insert(make_pair(n_g, EdgeProperties()));
+  graph[n_g].out_edges.insert(make_pair(n_h, EdgeProperties()));
+  graph[n_h].out_edges.insert(make_pair(n_g, EdgeProperties()));
+
+  CycleBreaker breaker;
+
+  set<Edge> broken_edges;
+  breaker.BreakCycles(graph, &broken_edges);
+
+  // The following cycles must be cut:
+  // A->E->B
+  // C->D->E
+  // G->H
+
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_a, n_e)) ||
+              utils::SetContainsKey(broken_edges, make_pair(n_e, n_b)) ||
+              utils::SetContainsKey(broken_edges, make_pair(n_b, n_a)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_c, n_d)) ||
+              utils::SetContainsKey(broken_edges, make_pair(n_d, n_e)) ||
+              utils::SetContainsKey(broken_edges, make_pair(n_e, n_c)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_g, n_h)) ||
+              utils::SetContainsKey(broken_edges, make_pair(n_h, n_g)));
+  EXPECT_EQ(3, broken_edges.size());
+}
+
+namespace {
+pair<Vertex::Index, EdgeProperties> EdgeWithWeight(Vertex::Index dest,
+uint64_t weight) {
+  EdgeProperties props;
+  props.extents.resize(1);
+  props.extents[0].set_num_blocks(weight);
+  return make_pair(dest, props);
+}
+}  // namespace
+
+
+// This creates a bunch of cycles like this:
+//
+//               root <------.
+//    (t)->     / | \        |
+//             V  V  V       |
+//             N  N  N       |
+//              \ | /        |
+//               VVV         |
+//                N          |
+//              / | \        |
+//             V  V  V       |
+//             N  N  N       |
+//               ...         |
+//     (s)->    \ | /        |
+//               VVV         |
+//                N          |
+//                 \_________/
+//
+// such that the original cutting algo would cut edges (s). We changed
+// the algorithm to cut cycles (t) instead, since they are closer to the
+// root, and that can massively speed up cycle cutting.
+TEST(CycleBreakerTest, AggressiveCutTest) {
+  int counter = 0;
+
+  const int kNodesPerGroup = 4;
+  const int kGroups = 33;
+
+  Graph graph(kGroups * kNodesPerGroup + 1);  // + 1 for the root node
+  SetOpForNodes(&graph);
+
+  const Vertex::Index n_root = counter++;
+
+  Vertex::Index last_hub = n_root;
+  for (int i = 0; i < kGroups; i++) {
+    uint64_t weight = 5;
+    if (i == 0)
+      weight = 2;
+    else if (i == (kGroups - 1))
+      weight = 1;
+
+    const Vertex::Index next_hub = counter++;
+
+    for (int j = 0; j < (kNodesPerGroup - 1); j++) {
+      const Vertex::Index node = counter++;
+      graph[last_hub].out_edges.insert(EdgeWithWeight(node, weight));
+      graph[node].out_edges.insert(EdgeWithWeight(next_hub, weight));
+    }
+    last_hub = next_hub;
+  }
+
+  graph[last_hub].out_edges.insert(EdgeWithWeight(n_root, 5));
+
+  EXPECT_EQ(counter, graph.size());
+
+  CycleBreaker breaker;
+
+  set<Edge> broken_edges;
+  LOG(INFO) << "If this hangs for more than 1 second, the test has failed.";
+  breaker.BreakCycles(graph, &broken_edges);
+
+  set<Edge> expected_cuts;
+
+  for (Vertex::EdgeMap::const_iterator it = graph[n_root].out_edges.begin(),
+       e = graph[n_root].out_edges.end(); it != e; ++it) {
+    expected_cuts.insert(make_pair(n_root, it->first));
+  }
+
+  EXPECT_TRUE(broken_edges == expected_cuts);
+}
+
+TEST(CycleBreakerTest, WeightTest) {
+  int counter = 0;
+  const Vertex::Index n_a = counter++;
+  const Vertex::Index n_b = counter++;
+  const Vertex::Index n_c = counter++;
+  const Vertex::Index n_d = counter++;
+  const Vertex::Index n_e = counter++;
+  const Vertex::Index n_f = counter++;
+  const Vertex::Index n_g = counter++;
+  const Vertex::Index n_h = counter++;
+  const Vertex::Index n_i = counter++;
+  const Vertex::Index n_j = counter++;
+  const Graph::size_type kNodeCount = counter++;
+
+  Graph graph(kNodeCount);
+  SetOpForNodes(&graph);
+
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_b, 4));
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_f, 3));
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_h, 2));
+  graph[n_b].out_edges.insert(EdgeWithWeight(n_a, 3));
+  graph[n_b].out_edges.insert(EdgeWithWeight(n_c, 4));
+  graph[n_c].out_edges.insert(EdgeWithWeight(n_b, 5));
+  graph[n_c].out_edges.insert(EdgeWithWeight(n_d, 3));
+  graph[n_d].out_edges.insert(EdgeWithWeight(n_a, 6));
+  graph[n_d].out_edges.insert(EdgeWithWeight(n_e, 3));
+  graph[n_e].out_edges.insert(EdgeWithWeight(n_d, 4));
+  graph[n_e].out_edges.insert(EdgeWithWeight(n_g, 5));
+  graph[n_f].out_edges.insert(EdgeWithWeight(n_g, 2));
+  graph[n_g].out_edges.insert(EdgeWithWeight(n_f, 3));
+  graph[n_g].out_edges.insert(EdgeWithWeight(n_d, 5));
+  graph[n_h].out_edges.insert(EdgeWithWeight(n_i, 8));
+  graph[n_i].out_edges.insert(EdgeWithWeight(n_e, 4));
+  graph[n_i].out_edges.insert(EdgeWithWeight(n_h, 9));
+  graph[n_i].out_edges.insert(EdgeWithWeight(n_j, 6));
+
+  CycleBreaker breaker;
+
+  set<Edge> broken_edges;
+  breaker.BreakCycles(graph, &broken_edges);
+
+  // These are required to be broken:
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_b, n_a)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_b, n_c)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_d, n_e)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_f, n_g)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_h, n_i)));
+}
+
+TEST(CycleBreakerTest, UnblockGraphTest) {
+  int counter = 0;
+  const Vertex::Index n_a = counter++;
+  const Vertex::Index n_b = counter++;
+  const Vertex::Index n_c = counter++;
+  const Vertex::Index n_d = counter++;
+  const Graph::size_type kNodeCount = counter++;
+
+  Graph graph(kNodeCount);
+  SetOpForNodes(&graph);
+
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_b, 1));
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_c, 1));
+  graph[n_b].out_edges.insert(EdgeWithWeight(n_c, 2));
+  graph[n_c].out_edges.insert(EdgeWithWeight(n_b, 2));
+  graph[n_b].out_edges.insert(EdgeWithWeight(n_d, 2));
+  graph[n_d].out_edges.insert(EdgeWithWeight(n_a, 2));
+
+  CycleBreaker breaker;
+
+  set<Edge> broken_edges;
+  breaker.BreakCycles(graph, &broken_edges);
+
+  // These are required to be broken:
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_a, n_b)));
+  EXPECT_TRUE(utils::SetContainsKey(broken_edges, make_pair(n_a, n_c)));
+}
+
+TEST(CycleBreakerTest, SkipOpsTest) {
+  int counter = 0;
+  const Vertex::Index n_a = counter++;
+  const Vertex::Index n_b = counter++;
+  const Vertex::Index n_c = counter++;
+  const Graph::size_type kNodeCount = counter++;
+
+  Graph graph(kNodeCount);
+  SetOpForNodes(&graph);
+  graph[n_a].aop.op.set_type(InstallOperation::REPLACE_BZ);
+  graph[n_c].aop.op.set_type(InstallOperation::REPLACE);
+
+  graph[n_a].out_edges.insert(EdgeWithWeight(n_b, 1));
+  graph[n_c].out_edges.insert(EdgeWithWeight(n_b, 1));
+
+  CycleBreaker breaker;
+
+  set<Edge> broken_edges;
+  breaker.BreakCycles(graph, &broken_edges);
+
+  EXPECT_EQ(2, breaker.skipped_ops());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/delta_diff_generator.cc b/payload_generator/delta_diff_generator.cc
new file mode 100644
index 0000000..ffe0fe9
--- /dev/null
+++ b/payload_generator/delta_diff_generator.cc
@@ -0,0 +1,148 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_generator/delta_diff_generator.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <inttypes.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+
+#include <algorithm>
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/logging.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/ab_generator.h"
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/payload_generator/delta_diff_utils.h"
+#include "update_engine/payload_generator/full_update_generator.h"
+#include "update_engine/payload_generator/inplace_generator.h"
+#include "update_engine/payload_generator/payload_file.h"
+
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+// bytes
+const size_t kRootFSPartitionSize = static_cast<size_t>(2) * 1024 * 1024 * 1024;
+const size_t kBlockSize = 4096;  // bytes
+
+bool GenerateUpdatePayloadFile(
+    const PayloadGenerationConfig& config,
+    const string& output_path,
+    const string& private_key_path,
+    uint64_t* metadata_size) {
+
+  // Create empty payload file object.
+  PayloadFile payload;
+  TEST_AND_RETURN_FALSE(payload.Init(config));
+
+  const string kTempFileTemplate("CrAU_temp_data.XXXXXX");
+  string temp_file_path;
+  int data_file_fd;
+  TEST_AND_RETURN_FALSE(
+      utils::MakeTempFile(kTempFileTemplate, &temp_file_path, &data_file_fd));
+  ScopedPathUnlinker temp_file_unlinker(temp_file_path);
+  TEST_AND_RETURN_FALSE(data_file_fd >= 0);
+
+  {
+    off_t data_file_size = 0;
+    ScopedFdCloser data_file_fd_closer(&data_file_fd);
+    BlobFileWriter blob_file(data_file_fd, &data_file_size);
+    if (config.is_delta) {
+      TEST_AND_RETURN_FALSE(config.source.partitions.size() ==
+                            config.target.partitions.size());
+    }
+    PartitionConfig empty_part("");
+    for (size_t i = 0; i < config.target.partitions.size(); i++) {
+      const PartitionConfig& old_part =
+          config.is_delta ? config.source.partitions[i] : empty_part;
+      const PartitionConfig& new_part = config.target.partitions[i];
+      LOG(INFO) << "Partition name: " << new_part.name;
+      LOG(INFO) << "Partition size: " << new_part.size;
+      LOG(INFO) << "Block count: " << new_part.size / config.block_size;
+
+      // Select payload generation strategy based on the config.
+      unique_ptr<OperationsGenerator> strategy;
+      // We don't efficiently support deltas on squashfs. For now, we will
+      // produce full operations in that case.
+      if (!old_part.path.empty() &&
+          !utils::IsSquashfsFilesystem(new_part.path)) {
+        // Delta update.
+        if (utils::IsExtFilesystem(new_part.path)) {
+          LOG_IF(WARNING, old_part.size != new_part.size)
+              << "Old and new filesystems have different size.";
+          // TODO(deymo): Our tools only support growing the filesystem size
+          // during an update. Remove this check when that's fixed.
+          // crbug.com/192136
+          LOG_IF(FATAL, old_part.size > new_part.size)
+              << "Shirking the filesystem size is not supported at the moment.";
+        }
+        if (config.minor_version == kInPlaceMinorPayloadVersion) {
+          LOG(INFO) << "Using generator InplaceGenerator().";
+          strategy.reset(new InplaceGenerator());
+        } else if (config.minor_version == kSourceMinorPayloadVersion ||
+                   config.minor_version == kOpSrcHashMinorPayloadVersion) {
+          LOG(INFO) << "Using generator ABGenerator().";
+          strategy.reset(new ABGenerator());
+        } else {
+          LOG(ERROR) << "Unsupported minor version given for delta payload: "
+                     << config.minor_version;
+          return false;
+        }
+      } else {
+        LOG(INFO) << "Using generator FullUpdateGenerator().";
+        strategy.reset(new FullUpdateGenerator());
+      }
+
+      vector<AnnotatedOperation> aops;
+      // Generate the operations using the strategy we selected above.
+      TEST_AND_RETURN_FALSE(strategy->GenerateOperations(config,
+                                                         old_part,
+                                                         new_part,
+                                                         &blob_file,
+                                                         &aops));
+
+      // Filter the no-operations. OperationsGenerators should not output this
+      // kind of operations normally, but this is an extra step to fix that if
+      // happened.
+      diff_utils::FilterNoopOperations(&aops);
+
+      TEST_AND_RETURN_FALSE(payload.AddPartition(old_part, new_part, aops));
+    }
+  }
+
+  LOG(INFO) << "Writing payload file...";
+  // Write payload file to disk.
+  TEST_AND_RETURN_FALSE(payload.WritePayload(output_path, temp_file_path,
+                                             private_key_path, metadata_size));
+
+  LOG(INFO) << "All done. Successfully created delta file with "
+            << "metadata size = " << *metadata_size;
+  return true;
+}
+
+};  // namespace chromeos_update_engine
diff --git a/payload_generator/delta_diff_generator.h b/payload_generator/delta_diff_generator.h
new file mode 100644
index 0000000..d8bdae2
--- /dev/null
+++ b/payload_generator/delta_diff_generator.h
@@ -0,0 +1,47 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_GENERATOR_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_GENERATOR_H_
+
+#include <string>
+
+#include "update_engine/payload_generator/payload_generation_config.h"
+
+namespace chromeos_update_engine {
+
+extern const size_t kBlockSize;
+extern const size_t kRootFSPartitionSize;
+
+// The |config| describes the payload generation request, describing both
+// old and new images for delta payloads and only the new image for full
+// payloads.
+// For delta payloads, the images should be already mounted read-only at
+// the respective rootfs_mountpt.
+// |private_key_path| points to a private key used to sign the update.
+// Pass empty string to not sign the update.
+// |output_path| is the filename where the delta update should be written.
+// Returns true on success. Also writes the size of the metadata into
+// |metadata_size|.
+bool GenerateUpdatePayloadFile(const PayloadGenerationConfig& config,
+                               const std::string& output_path,
+                               const std::string& private_key_path,
+                               uint64_t* metadata_size);
+
+
+};  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_GENERATOR_H_
diff --git a/payload_generator/delta_diff_utils.cc b/payload_generator/delta_diff_utils.cc
new file mode 100644
index 0000000..ba1aac4
--- /dev/null
+++ b/payload_generator/delta_diff_utils.cc
@@ -0,0 +1,679 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/delta_diff_utils.h"
+
+#include <algorithm>
+#include <map>
+
+#include <base/files/file_util.h>
+#include <base/format_macros.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/block_mapping.h"
+#include "update_engine/payload_generator/bzip.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using std::map;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+namespace {
+
+const char* const kBsdiffPath = "bsdiff";
+
+// The maximum destination size allowed for bsdiff. In general, bsdiff should
+// work for arbitrary big files, but the payload generation and payload
+// application requires a significant amount of RAM. We put a hard-limit of
+// 200 MiB that should not affect any released board, but will limit the
+// Chrome binary in ASan builders.
+const uint64_t kMaxBsdiffDestinationSize = 200 * 1024 * 1024;  // bytes
+
+// Process a range of blocks from |range_start| to |range_end| in the extent at
+// position |*idx_p| of |extents|. If |do_remove| is true, this range will be
+// removed, which may cause the extent to be trimmed, split or removed entirely.
+// The value of |*idx_p| is updated to point to the next extent to be processed.
+// Returns true iff the next extent to process is a new or updated one.
+bool ProcessExtentBlockRange(vector<Extent>* extents, size_t* idx_p,
+                             const bool do_remove, uint64_t range_start,
+                             uint64_t range_end) {
+  size_t idx = *idx_p;
+  uint64_t start_block = (*extents)[idx].start_block();
+  uint64_t num_blocks = (*extents)[idx].num_blocks();
+  uint64_t range_size = range_end - range_start;
+
+  if (do_remove) {
+    if (range_size == num_blocks) {
+      // Remove the entire extent.
+      extents->erase(extents->begin() + idx);
+    } else if (range_end == num_blocks) {
+      // Trim the end of the extent.
+      (*extents)[idx].set_num_blocks(num_blocks - range_size);
+      idx++;
+    } else if (range_start == 0) {
+      // Trim the head of the extent.
+      (*extents)[idx].set_start_block(start_block + range_size);
+      (*extents)[idx].set_num_blocks(num_blocks - range_size);
+    } else {
+      // Trim the middle, splitting the remainder into two parts.
+      (*extents)[idx].set_num_blocks(range_start);
+      Extent e;
+      e.set_start_block(start_block + range_end);
+      e.set_num_blocks(num_blocks - range_end);
+      idx++;
+      extents->insert(extents->begin() + idx, e);
+    }
+  } else if (range_end == num_blocks) {
+    // Done with this extent.
+    idx++;
+  } else {
+    return false;
+  }
+
+  *idx_p = idx;
+  return true;
+}
+
+// Remove identical corresponding block ranges in |src_extents| and
+// |dst_extents|. Used for preventing moving of blocks onto themselves during
+// MOVE operations. The value of |total_bytes| indicates the actual length of
+// content; this may be slightly less than the total size of blocks, in which
+// case the last block is only partly occupied with data. Returns the total
+// number of bytes removed.
+size_t RemoveIdenticalBlockRanges(vector<Extent>* src_extents,
+                                  vector<Extent>* dst_extents,
+                                  const size_t total_bytes) {
+  size_t src_idx = 0;
+  size_t dst_idx = 0;
+  uint64_t src_offset = 0, dst_offset = 0;
+  bool new_src = true, new_dst = true;
+  size_t removed_bytes = 0, nonfull_block_bytes;
+  bool do_remove = false;
+  while (src_idx < src_extents->size() && dst_idx < dst_extents->size()) {
+    if (new_src) {
+      src_offset = 0;
+      new_src = false;
+    }
+    if (new_dst) {
+      dst_offset = 0;
+      new_dst = false;
+    }
+
+    do_remove = ((*src_extents)[src_idx].start_block() + src_offset ==
+                 (*dst_extents)[dst_idx].start_block() + dst_offset);
+
+    uint64_t src_num_blocks = (*src_extents)[src_idx].num_blocks();
+    uint64_t dst_num_blocks = (*dst_extents)[dst_idx].num_blocks();
+    uint64_t min_num_blocks = std::min(src_num_blocks - src_offset,
+                                       dst_num_blocks - dst_offset);
+    uint64_t prev_src_offset = src_offset;
+    uint64_t prev_dst_offset = dst_offset;
+    src_offset += min_num_blocks;
+    dst_offset += min_num_blocks;
+
+    new_src = ProcessExtentBlockRange(src_extents, &src_idx, do_remove,
+                                      prev_src_offset, src_offset);
+    new_dst = ProcessExtentBlockRange(dst_extents, &dst_idx, do_remove,
+                                      prev_dst_offset, dst_offset);
+    if (do_remove)
+      removed_bytes += min_num_blocks * kBlockSize;
+  }
+
+  // If we removed the last block and this block is only partly used by file
+  // content, deduct the unused portion from the total removed byte count.
+  if (do_remove && (nonfull_block_bytes = total_bytes % kBlockSize))
+    removed_bytes -= kBlockSize - nonfull_block_bytes;
+
+  return removed_bytes;
+}
+
+}  // namespace
+
+namespace diff_utils {
+
+bool DeltaReadPartition(
+    vector<AnnotatedOperation>* aops,
+    const PartitionConfig& old_part,
+    const PartitionConfig& new_part,
+    ssize_t hard_chunk_blocks,
+    size_t soft_chunk_blocks,
+    BlobFileWriter* blob_file,
+    bool src_ops_allowed) {
+  ExtentRanges old_visited_blocks;
+  ExtentRanges new_visited_blocks;
+
+  TEST_AND_RETURN_FALSE(DeltaMovedAndZeroBlocks(
+      aops,
+      old_part.path,
+      new_part.path,
+      old_part.fs_interface ? old_part.fs_interface->GetBlockCount() : 0,
+      new_part.fs_interface->GetBlockCount(),
+      soft_chunk_blocks,
+      src_ops_allowed,
+      blob_file,
+      &old_visited_blocks,
+      &new_visited_blocks));
+
+  map<string, vector<Extent>> old_files_map;
+  if (old_part.fs_interface) {
+    vector<FilesystemInterface::File> old_files;
+    old_part.fs_interface->GetFiles(&old_files);
+    for (const FilesystemInterface::File& file : old_files)
+      old_files_map[file.name] = file.extents;
+  }
+
+  TEST_AND_RETURN_FALSE(new_part.fs_interface);
+  vector<FilesystemInterface::File> new_files;
+  new_part.fs_interface->GetFiles(&new_files);
+
+  // The processing is very straightforward here, we generate operations for
+  // every file (and pseudo-file such as the metadata) in the new filesystem
+  // based on the file with the same name in the old filesystem, if any.
+  // Files with overlapping data blocks (like hardlinks or filesystems with tail
+  // packing or compression where the blocks store more than one file) are only
+  // generated once in the new image, but are also used only once from the old
+  // image due to some simplifications (see below).
+  for (const FilesystemInterface::File& new_file : new_files) {
+    // Ignore the files in the new filesystem without blocks. Symlinks with
+    // data blocks (for example, symlinks bigger than 60 bytes in ext2) are
+    // handled as normal files. We also ignore blocks that were already
+    // processed by a previous file.
+    vector<Extent> new_file_extents = FilterExtentRanges(
+        new_file.extents, new_visited_blocks);
+    new_visited_blocks.AddExtents(new_file_extents);
+
+    if (new_file_extents.empty())
+      continue;
+
+    LOG(INFO) << "Encoding file " << new_file.name << " ("
+              << BlocksInExtents(new_file_extents) << " blocks)";
+
+    // We can't visit each dst image inode more than once, as that would
+    // duplicate work. Here, we avoid visiting each source image inode
+    // more than once. Technically, we could have multiple operations
+    // that read the same blocks from the source image for diffing, but
+    // we choose not to avoid complexity. Eventually we will move away
+    // from using a graph/cycle detection/etc to generate diffs, and at that
+    // time, it will be easy (non-complex) to have many operations read
+    // from the same source blocks. At that time, this code can die. -adlr
+    vector<Extent> old_file_extents = FilterExtentRanges(
+        old_files_map[new_file.name], old_visited_blocks);
+    old_visited_blocks.AddExtents(old_file_extents);
+
+    TEST_AND_RETURN_FALSE(DeltaReadFile(
+        aops,
+        old_part.path,
+        new_part.path,
+        old_file_extents,
+        new_file_extents,
+        new_file.name,  // operation name
+        hard_chunk_blocks,
+        blob_file,
+        src_ops_allowed));
+  }
+  // Process all the blocks not included in any file. We provided all the unused
+  // blocks in the old partition as available data.
+  vector<Extent> new_unvisited = {
+      ExtentForRange(0, new_part.size / kBlockSize)};
+  new_unvisited = FilterExtentRanges(new_unvisited, new_visited_blocks);
+  if (new_unvisited.empty())
+    return true;
+
+  vector<Extent> old_unvisited;
+  if (old_part.fs_interface) {
+    old_unvisited.push_back(ExtentForRange(0, old_part.size / kBlockSize));
+    old_unvisited = FilterExtentRanges(old_unvisited, old_visited_blocks);
+  }
+
+  LOG(INFO) << "Scanning " << BlocksInExtents(new_unvisited)
+            << " unwritten blocks using chunk size of "
+            << soft_chunk_blocks << " blocks.";
+  // We use the soft_chunk_blocks limit for the <non-file-data> as we don't
+  // really know the structure of this data and we should not expect it to have
+  // redundancy between partitions.
+  TEST_AND_RETURN_FALSE(DeltaReadFile(
+      aops,
+      old_part.path,
+      new_part.path,
+      old_unvisited,
+      new_unvisited,
+      "<non-file-data>",  // operation name
+      soft_chunk_blocks,
+      blob_file,
+      src_ops_allowed));
+
+  return true;
+}
+
+bool DeltaMovedAndZeroBlocks(
+    vector<AnnotatedOperation>* aops,
+    const string& old_part,
+    const string& new_part,
+    size_t old_num_blocks,
+    size_t new_num_blocks,
+    ssize_t chunk_blocks,
+    bool src_ops_allowed,
+    BlobFileWriter* blob_file,
+    ExtentRanges* old_visited_blocks,
+    ExtentRanges* new_visited_blocks) {
+  vector<BlockMapping::BlockId> old_block_ids;
+  vector<BlockMapping::BlockId> new_block_ids;
+  TEST_AND_RETURN_FALSE(MapPartitionBlocks(old_part,
+                                           new_part,
+                                           old_num_blocks * kBlockSize,
+                                           new_num_blocks * kBlockSize,
+                                           kBlockSize,
+                                           &old_block_ids,
+                                           &new_block_ids));
+
+  // For minor-version=1, we map all the blocks that didn't move, regardless of
+  // the contents since they are already copied and no operation is required.
+  if (!src_ops_allowed) {
+    uint64_t num_blocks = std::min(old_num_blocks, new_num_blocks);
+    for (uint64_t block = 0; block < num_blocks; block++) {
+      if (old_block_ids[block] == new_block_ids[block] &&
+          !old_visited_blocks->ContainsBlock(block) &&
+          !new_visited_blocks->ContainsBlock(block)) {
+        old_visited_blocks->AddBlock(block);
+        new_visited_blocks->AddBlock(block);
+      }
+    }
+  }
+
+  // A mapping from the block_id to the list of block numbers with that block id
+  // in the old partition. This is used to lookup where in the old partition
+  // is a block from the new partition.
+  map<BlockMapping::BlockId, vector<uint64_t>> old_blocks_map;
+
+  for (uint64_t block = old_num_blocks; block-- > 0; ) {
+    if (old_block_ids[block] != 0 && !old_visited_blocks->ContainsBlock(block))
+      old_blocks_map[old_block_ids[block]].push_back(block);
+  }
+
+  // The collection of blocks in the new partition with just zeros. This is a
+  // common case for free-space that's also problematic for bsdiff, so we want
+  // to optimize it using REPLACE_BZ operations. The blob for a REPLACE_BZ of
+  // just zeros is so small that it doesn't make sense to spend the I/O reading
+  // zeros from the old partition.
+  vector<Extent> new_zeros;
+
+  vector<Extent> old_identical_blocks;
+  vector<Extent> new_identical_blocks;
+
+  for (uint64_t block = 0; block < new_num_blocks; block++) {
+    // Only produce operations for blocks that were not yet visited.
+    if (new_visited_blocks->ContainsBlock(block))
+      continue;
+    if (new_block_ids[block] == 0) {
+      AppendBlockToExtents(&new_zeros, block);
+      continue;
+    }
+
+    auto old_blocks_map_it = old_blocks_map.find(new_block_ids[block]);
+    // Check if the block exists in the old partition at all.
+    if (old_blocks_map_it == old_blocks_map.end() ||
+        old_blocks_map_it->second.empty())
+      continue;
+
+    AppendBlockToExtents(&old_identical_blocks,
+                         old_blocks_map_it->second.back());
+    AppendBlockToExtents(&new_identical_blocks, block);
+    // We can't reuse source blocks in minor version 1 because the cycle
+    // breaking algorithm doesn't support that.
+    if (!src_ops_allowed)
+      old_blocks_map_it->second.pop_back();
+  }
+
+  // Produce operations for the zero blocks split per output extent.
+  size_t num_ops = aops->size();
+  new_visited_blocks->AddExtents(new_zeros);
+  for (Extent extent : new_zeros) {
+    TEST_AND_RETURN_FALSE(DeltaReadFile(
+        aops,
+        "",
+        new_part,
+        vector<Extent>(),  // old_extents
+        vector<Extent>{extent},  // new_extents
+        "<zeros>",
+        chunk_blocks,
+        blob_file,
+        src_ops_allowed));
+  }
+  LOG(INFO) << "Produced " << (aops->size() - num_ops) << " operations for "
+            << BlocksInExtents(new_zeros) << " zeroed blocks";
+
+  // Produce MOVE/SOURCE_COPY operations for the moved blocks.
+  num_ops = aops->size();
+  if (chunk_blocks == -1)
+    chunk_blocks = new_num_blocks;
+  uint64_t used_blocks = 0;
+  old_visited_blocks->AddExtents(old_identical_blocks);
+  new_visited_blocks->AddExtents(new_identical_blocks);
+  for (Extent extent : new_identical_blocks) {
+    // We split the operation at the extent boundary or when bigger than
+    // chunk_blocks.
+    for (uint64_t op_block_offset = 0; op_block_offset < extent.num_blocks();
+         op_block_offset += chunk_blocks) {
+      aops->emplace_back();
+      AnnotatedOperation* aop = &aops->back();
+      aop->name = "<identical-blocks>";
+      aop->op.set_type(src_ops_allowed ? InstallOperation::SOURCE_COPY
+                                       : InstallOperation::MOVE);
+
+      uint64_t chunk_num_blocks =
+        std::min(extent.num_blocks() - op_block_offset,
+                 static_cast<uint64_t>(chunk_blocks));
+
+      // The current operation represents the move/copy operation for the
+      // sublist starting at |used_blocks| of length |chunk_num_blocks| where
+      // the src and dst are from |old_identical_blocks| and
+      // |new_identical_blocks| respectively.
+      StoreExtents(
+          ExtentsSublist(old_identical_blocks, used_blocks, chunk_num_blocks),
+          aop->op.mutable_src_extents());
+
+      Extent* op_dst_extent = aop->op.add_dst_extents();
+      op_dst_extent->set_start_block(extent.start_block() + op_block_offset);
+      op_dst_extent->set_num_blocks(chunk_num_blocks);
+      CHECK(
+          vector<Extent>{*op_dst_extent} ==  // NOLINT(whitespace/braces)
+          ExtentsSublist(new_identical_blocks, used_blocks, chunk_num_blocks));
+
+      used_blocks += chunk_num_blocks;
+    }
+  }
+  LOG(INFO) << "Produced " << (aops->size() - num_ops) << " operations for "
+            << used_blocks << " identical blocks moved";
+
+  return true;
+}
+
+bool DeltaReadFile(
+    vector<AnnotatedOperation>* aops,
+    const string& old_part,
+    const string& new_part,
+    const vector<Extent>& old_extents,
+    const vector<Extent>& new_extents,
+    const string& name,
+    ssize_t chunk_blocks,
+    BlobFileWriter* blob_file,
+    bool src_ops_allowed) {
+  brillo::Blob data;
+  InstallOperation operation;
+
+  uint64_t total_blocks = BlocksInExtents(new_extents);
+  if (chunk_blocks == -1)
+    chunk_blocks = total_blocks;
+
+  // If bsdiff breaks again, blacklist the problem file by using:
+  //   bsdiff_allowed = (name != "/foo/bar")
+  //
+  // TODO(dgarrett): chromium-os:15274 connect this test to the command line.
+  bool bsdiff_allowed = true;
+  if (static_cast<uint64_t>(chunk_blocks) * kBlockSize >
+      kMaxBsdiffDestinationSize) {
+    bsdiff_allowed = false;
+  }
+
+  if (!bsdiff_allowed) {
+    LOG(INFO) << "bsdiff blacklisting: " << name;
+  }
+
+  for (uint64_t block_offset = 0; block_offset < total_blocks;
+      block_offset += chunk_blocks) {
+    // Split the old/new file in the same chunks. Note that this could drop
+    // some information from the old file used for the new chunk. If the old
+    // file is smaller (or even empty when there's no old file) the chunk will
+    // also be empty.
+    vector<Extent> old_extents_chunk = ExtentsSublist(
+        old_extents, block_offset, chunk_blocks);
+    vector<Extent> new_extents_chunk = ExtentsSublist(
+        new_extents, block_offset, chunk_blocks);
+    NormalizeExtents(&old_extents_chunk);
+    NormalizeExtents(&new_extents_chunk);
+
+    TEST_AND_RETURN_FALSE(ReadExtentsToDiff(old_part,
+                                            new_part,
+                                            old_extents_chunk,
+                                            new_extents_chunk,
+                                            bsdiff_allowed,
+                                            &data,
+                                            &operation,
+                                            src_ops_allowed));
+
+    // Check if the operation writes nothing.
+    if (operation.dst_extents_size() == 0) {
+      if (operation.type() == InstallOperation::MOVE) {
+        LOG(INFO) << "Empty MOVE operation ("
+                  << name << "), skipping";
+        continue;
+      } else {
+        LOG(ERROR) << "Empty non-MOVE operation";
+        return false;
+      }
+    }
+
+    // Now, insert into the list of operations.
+    AnnotatedOperation aop;
+    aop.name = name;
+    if (static_cast<uint64_t>(chunk_blocks) < total_blocks) {
+      aop.name = base::StringPrintf("%s:%" PRIu64,
+                                    name.c_str(), block_offset / chunk_blocks);
+    }
+    aop.op = operation;
+
+    // Write the data
+    if (operation.type() != InstallOperation::MOVE &&
+        operation.type() != InstallOperation::SOURCE_COPY) {
+      TEST_AND_RETURN_FALSE(aop.SetOperationBlob(&data, blob_file));
+    } else {
+      TEST_AND_RETURN_FALSE(blob_file->StoreBlob(data) != -1);
+    }
+    aops->emplace_back(aop);
+  }
+  return true;
+}
+
+bool ReadExtentsToDiff(const string& old_part,
+                       const string& new_part,
+                       const vector<Extent>& old_extents,
+                       const vector<Extent>& new_extents,
+                       bool bsdiff_allowed,
+                       brillo::Blob* out_data,
+                       InstallOperation* out_op,
+                       bool src_ops_allowed) {
+  InstallOperation operation;
+  // Data blob that will be written to delta file.
+  const brillo::Blob* data_blob = nullptr;
+
+  // We read blocks from old_extents and write blocks to new_extents.
+  uint64_t blocks_to_read = BlocksInExtents(old_extents);
+  uint64_t blocks_to_write = BlocksInExtents(new_extents);
+
+  // Make copies of the extents so we can modify them.
+  vector<Extent> src_extents = old_extents;
+  vector<Extent> dst_extents = new_extents;
+
+  // Read in bytes from new data.
+  brillo::Blob new_data;
+  TEST_AND_RETURN_FALSE(utils::ReadExtents(new_part,
+                                           new_extents,
+                                           &new_data,
+                                           kBlockSize * blocks_to_write,
+                                           kBlockSize));
+  TEST_AND_RETURN_FALSE(!new_data.empty());
+
+
+  // Using a REPLACE is always an option.
+  operation.set_type(InstallOperation::REPLACE);
+  data_blob = &new_data;
+
+  // Try compressing it with bzip2.
+  brillo::Blob new_data_bz;
+  TEST_AND_RETURN_FALSE(BzipCompress(new_data, &new_data_bz));
+  CHECK(!new_data_bz.empty());
+  if (new_data_bz.size() < data_blob->size()) {
+    // A REPLACE_BZ is better.
+    operation.set_type(InstallOperation::REPLACE_BZ);
+    data_blob = &new_data_bz;
+  }
+
+  brillo::Blob old_data;
+  brillo::Blob empty_blob;
+  brillo::Blob bsdiff_delta;
+  if (blocks_to_read > 0) {
+    // Read old data.
+    TEST_AND_RETURN_FALSE(
+        utils::ReadExtents(old_part, src_extents, &old_data,
+                           kBlockSize * blocks_to_read, kBlockSize));
+    if (old_data == new_data) {
+      // No change in data.
+      if (src_ops_allowed) {
+        operation.set_type(InstallOperation::SOURCE_COPY);
+      } else {
+        operation.set_type(InstallOperation::MOVE);
+      }
+      data_blob = &empty_blob;
+    } else if (bsdiff_allowed) {
+      // If the source file is considered bsdiff safe (no bsdiff bugs
+      // triggered), see if BSDIFF encoding is smaller.
+      base::FilePath old_chunk;
+      TEST_AND_RETURN_FALSE(base::CreateTemporaryFile(&old_chunk));
+      ScopedPathUnlinker old_unlinker(old_chunk.value());
+      TEST_AND_RETURN_FALSE(
+          utils::WriteFile(old_chunk.value().c_str(),
+                           old_data.data(), old_data.size()));
+      base::FilePath new_chunk;
+      TEST_AND_RETURN_FALSE(base::CreateTemporaryFile(&new_chunk));
+      ScopedPathUnlinker new_unlinker(new_chunk.value());
+      TEST_AND_RETURN_FALSE(
+          utils::WriteFile(new_chunk.value().c_str(),
+                           new_data.data(), new_data.size()));
+
+      TEST_AND_RETURN_FALSE(
+          BsdiffFiles(old_chunk.value(), new_chunk.value(), &bsdiff_delta));
+      CHECK_GT(bsdiff_delta.size(), static_cast<brillo::Blob::size_type>(0));
+      if (bsdiff_delta.size() < data_blob->size()) {
+        if (src_ops_allowed) {
+          operation.set_type(InstallOperation::SOURCE_BSDIFF);
+        } else {
+          operation.set_type(InstallOperation::BSDIFF);
+        }
+        data_blob = &bsdiff_delta;
+      }
+    }
+  }
+
+  size_t removed_bytes = 0;
+  // Remove identical src/dst block ranges in MOVE operations.
+  if (operation.type() == InstallOperation::MOVE) {
+    removed_bytes = RemoveIdenticalBlockRanges(
+        &src_extents, &dst_extents, new_data.size());
+  }
+  // Set legacy src_length and dst_length fields.
+  operation.set_src_length(old_data.size() - removed_bytes);
+  operation.set_dst_length(new_data.size() - removed_bytes);
+
+  // Embed extents in the operation.
+  StoreExtents(src_extents, operation.mutable_src_extents());
+  StoreExtents(dst_extents, operation.mutable_dst_extents());
+
+  // Replace operations should not have source extents.
+  if (operation.type() == InstallOperation::REPLACE ||
+      operation.type() == InstallOperation::REPLACE_BZ) {
+    operation.clear_src_extents();
+    operation.clear_src_length();
+  }
+
+  *out_data = std::move(*data_blob);
+  *out_op = operation;
+
+  return true;
+}
+
+// Runs the bsdiff tool on two files and returns the resulting delta in
+// 'out'. Returns true on success.
+bool BsdiffFiles(const string& old_file,
+                 const string& new_file,
+                 brillo::Blob* out) {
+  const string kPatchFile = "delta.patchXXXXXX";
+  string patch_file_path;
+
+  TEST_AND_RETURN_FALSE(
+      utils::MakeTempFile(kPatchFile, &patch_file_path, nullptr));
+
+  vector<string> cmd;
+  cmd.push_back(kBsdiffPath);
+  cmd.push_back(old_file);
+  cmd.push_back(new_file);
+  cmd.push_back(patch_file_path);
+
+  int rc = 1;
+  brillo::Blob patch_file;
+  TEST_AND_RETURN_FALSE(Subprocess::SynchronousExec(cmd, &rc, nullptr));
+  TEST_AND_RETURN_FALSE(rc == 0);
+  TEST_AND_RETURN_FALSE(utils::ReadFile(patch_file_path, out));
+  unlink(patch_file_path.c_str());
+  return true;
+}
+
+// Returns true if |op| is a no-op operation that doesn't do any useful work
+// (e.g., a move operation that copies blocks onto themselves).
+bool IsNoopOperation(const InstallOperation& op) {
+  return (op.type() == InstallOperation::MOVE &&
+          ExpandExtents(op.src_extents()) == ExpandExtents(op.dst_extents()));
+}
+
+void FilterNoopOperations(vector<AnnotatedOperation>* ops) {
+  ops->erase(
+      std::remove_if(
+          ops->begin(), ops->end(),
+          [](const AnnotatedOperation& aop){return IsNoopOperation(aop.op);}),
+      ops->end());
+}
+
+bool InitializePartitionInfo(const PartitionConfig& part, PartitionInfo* info) {
+  info->set_size(part.size);
+  HashCalculator hasher;
+  TEST_AND_RETURN_FALSE(hasher.UpdateFile(part.path, part.size) ==
+                        static_cast<off_t>(part.size));
+  TEST_AND_RETURN_FALSE(hasher.Finalize());
+  const brillo::Blob& hash = hasher.raw_hash();
+  info->set_hash(hash.data(), hash.size());
+  LOG(INFO) << part.path << ": size=" << part.size << " hash=" << hasher.hash();
+  return true;
+}
+
+bool CompareAopsByDestination(AnnotatedOperation first_aop,
+                              AnnotatedOperation second_aop) {
+  // We want empty operations to be at the end of the payload.
+  if (!first_aop.op.dst_extents().size() || !second_aop.op.dst_extents().size())
+    return ((!first_aop.op.dst_extents().size()) <
+            (!second_aop.op.dst_extents().size()));
+  uint32_t first_dst_start = first_aop.op.dst_extents(0).start_block();
+  uint32_t second_dst_start = second_aop.op.dst_extents(0).start_block();
+  return first_dst_start < second_dst_start;
+}
+
+}  // namespace diff_utils
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/delta_diff_utils.h b/payload_generator/delta_diff_utils.h
new file mode 100644
index 0000000..5ba9bc7
--- /dev/null
+++ b/payload_generator/delta_diff_utils.h
@@ -0,0 +1,137 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_UTILS_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_UTILS_H_
+
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+namespace diff_utils {
+
+// Create operations in |aops| to produce all the blocks in the |new_part|
+// partition using the filesystem opened in that PartitionConfig.
+// It uses the files reported by the filesystem in |old_part| and the data
+// blocks in that partition (if available) to determine the best way to compress
+// the new files (REPLACE, REPLACE_BZ, COPY, BSDIFF) and writes any necessary
+// data to the end of |data_fd| updating |data_file_size| accordingly.
+// |hard_chunk_blocks| and |soft_chunk_blocks| are the hard and soft chunk
+// limits in number of blocks respectively. The soft chunk limit is used to
+// split MOVE and SOURCE_COPY operations and REPLACE_BZ of zeroed blocks, while
+// the hard limit is used to split a file when generating other operations. A
+// value of -1 in |hard_chunk_blocks| means whole files.
+bool DeltaReadPartition(std::vector<AnnotatedOperation>* aops,
+                        const PartitionConfig& old_part,
+                        const PartitionConfig& new_part,
+                        ssize_t hard_chunk_blocks,
+                        size_t soft_chunk_blocks,
+                        BlobFileWriter* blob_file,
+                        bool src_ops_allowed);
+
+// Create operations in |aops| for identical blocks that moved around in the old
+// and new partition and also handle zeroed blocks. The old and new partition
+// are stored in the |old_part| and |new_part| files and have |old_num_blocks|
+// and |new_num_blocks| respectively. The maximum operation size is
+// |chunk_blocks| blocks, or unlimited if |chunk_blocks| is -1. The blobs of the
+// produced operations are stored in the |data_fd| file whose size is updated
+// in the value pointed by |data_file_size|.
+// The collections |old_visited_blocks| and |new_visited_blocks| state what
+// blocks already have operations reading or writing them and only operations
+// for unvisited blocks are produced by this function updating both collections
+// with the used blocks.
+bool DeltaMovedAndZeroBlocks(std::vector<AnnotatedOperation>* aops,
+                             const std::string& old_part,
+                             const std::string& new_part,
+                             size_t old_num_blocks,
+                             size_t new_num_blocks,
+                             ssize_t chunk_blocks,
+                             bool src_ops_allowed,
+                             BlobFileWriter* blob_file,
+                             ExtentRanges* old_visited_blocks,
+                             ExtentRanges* new_visited_blocks);
+
+// For a given file |name| append operations to |aops| to produce it in the
+// |new_part|. The file will be split in chunks of |chunk_blocks| blocks each
+// or treated as a single chunk if |chunk_blocks| is -1. The file data is
+// stored in |new_part| in the blocks described by |new_extents| and, if it
+// exists, the old version exists in |old_part| in the blocks described by
+// |old_extents|. The operations added to |aops| reference the data blob
+// in the file |data_fd|, which has length *data_file_size. *data_file_size is
+// updated appropriately. Returns true on success.
+bool DeltaReadFile(std::vector<AnnotatedOperation>* aops,
+                   const std::string& old_part,
+                   const std::string& new_part,
+                   const std::vector<Extent>& old_extents,
+                   const std::vector<Extent>& new_extents,
+                   const std::string& name,
+                   ssize_t chunk_blocks,
+                   BlobFileWriter* blob_file,
+                   bool src_ops_allowed);
+
+// Reads the blocks |old_extents| from |old_part| (if it exists) and the
+// |new_extents| from |new_part| and determines the smallest way to encode
+// this |new_extents| for the diff. It stores necessary data in |out_data| and
+// fills in |out_op|. If there's no change in old and new files, it creates a
+// MOVE operation. If there is a change, the smallest of REPLACE, REPLACE_BZ,
+// or BSDIFF wins. |new_extents| must not be empty.
+// If |src_ops_allowed| is true, it will emit SOURCE_COPY and SOURCE_BSDIFF
+// operations instead of MOVE and BSDIFF, respectively.
+// Returns true on success.
+bool ReadExtentsToDiff(const std::string& old_part,
+                       const std::string& new_part,
+                       const std::vector<Extent>& old_extents,
+                       const std::vector<Extent>& new_extents,
+                       bool bsdiff_allowed,
+                       brillo::Blob* out_data,
+                       InstallOperation* out_op,
+                       bool src_ops_allowed);
+
+// Runs the bsdiff tool on two files and returns the resulting delta in
+// |out|. Returns true on success.
+bool BsdiffFiles(const std::string& old_file,
+                 const std::string& new_file,
+                 brillo::Blob* out);
+
+// Returns true if |op| is a no-op operation that doesn't do any useful work
+// (e.g., a move operation that copies blocks onto themselves).
+bool IsNoopOperation(const InstallOperation& op);
+
+// Filters all the operations that are no-op, maintaining the relative order
+// of the rest of the operations.
+void FilterNoopOperations(std::vector<AnnotatedOperation>* ops);
+
+bool InitializePartitionInfo(const PartitionConfig& partition,
+                             PartitionInfo* info);
+
+// Compare two AnnotatedOperations by the start block of the first Extent in
+// their destination extents.
+bool CompareAopsByDestination(AnnotatedOperation first_aop,
+                              AnnotatedOperation second_aop);
+
+}  // namespace diff_utils
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_DELTA_DIFF_UTILS_H_
diff --git a/payload_generator/delta_diff_utils_unittest.cc b/payload_generator/delta_diff_utils_unittest.cc
new file mode 100644
index 0000000..4dc5981
--- /dev/null
+++ b/payload_generator/delta_diff_utils_unittest.cc
@@ -0,0 +1,775 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/delta_diff_utils.h"
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <base/files/scoped_file.h>
+#include <base/format_macros.h>
+#include <base/strings/stringprintf.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/extent_utils.h"
+#include "update_engine/payload_generator/fake_filesystem.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// Writes the |data| in the blocks specified by |extents| on the partition
+// |part_path|. The |data| size could be smaller than the size of the blocks
+// passed.
+bool WriteExtents(const string& part_path,
+                  const vector<Extent>& extents,
+                  off_t block_size,
+                  const brillo::Blob& data) {
+  uint64_t offset = 0;
+  base::ScopedFILE fp(fopen(part_path.c_str(), "r+"));
+  TEST_AND_RETURN_FALSE(fp.get());
+
+  for (const Extent& extent : extents) {
+    if (offset >= data.size())
+      break;
+    TEST_AND_RETURN_FALSE(
+        fseek(fp.get(), extent.start_block() * block_size, SEEK_SET) == 0);
+    uint64_t to_write = std::min(extent.num_blocks() * block_size,
+                                 data.size() - offset);
+    TEST_AND_RETURN_FALSE(
+        fwrite(data.data() + offset, 1, to_write, fp.get()) == to_write);
+    offset += extent.num_blocks() * block_size;
+  }
+  return true;
+}
+
+// Create a fake filesystem of the given |size| and initialize the partition
+// holding it in the PartitionConfig |part|.
+void CreatePartition(PartitionConfig* part, const string& pattern,
+                     uint64_t block_size, off_t size) {
+  int fd = -1;
+  ASSERT_TRUE(utils::MakeTempFile(pattern.c_str(), &part->path, &fd));
+  ASSERT_EQ(0, ftruncate(fd, size));
+  ASSERT_EQ(0, close(fd));
+  part->fs_interface.reset(new FakeFilesystem(block_size, size / block_size));
+  part->size = size;
+}
+
+// Writes to the |partition| path blocks such they are all different and they
+// include the tag passed in |tag|, making them also different to any other
+// block on a partition initialized with this function with a different tag.
+// The |block_size| should be a divisor of the partition size.
+// Returns whether the function succeeded writing the partition.
+bool InitializePartitionWithUniqueBlocks(const PartitionConfig& part,
+                                         uint64_t block_size,
+                                         uint64_t tag) {
+  TEST_AND_RETURN_FALSE(part.size % block_size == 0);
+  size_t num_blocks = part.size / block_size;
+  brillo::Blob file_data(part.size);
+  for (size_t i = 0; i < num_blocks; ++i) {
+    string prefix = base::StringPrintf(
+        "block tag 0x%.16" PRIx64 ", block number %16" PRIuS " ", tag, i);
+    brillo::Blob block_data(prefix.begin(), prefix.end());
+    TEST_AND_RETURN_FALSE(prefix.size() <= block_size);
+    block_data.resize(block_size, 'X');
+    std::copy(block_data.begin(), block_data.end(),
+              file_data.begin() + i * block_size);
+  }
+  return test_utils::WriteFileVector(part.path, file_data);
+}
+
+}  // namespace
+
+class DeltaDiffUtilsTest : public ::testing::Test {
+ protected:
+  const uint64_t kDefaultBlockCount = 128;
+
+  void SetUp() override {
+    CreatePartition(&old_part_, "DeltaDiffUtilsTest-old_part-XXXXXX",
+                    block_size_, block_size_ * kDefaultBlockCount);
+    CreatePartition(&new_part_, "DeltaDiffUtilsTest-old_part-XXXXXX",
+                    block_size_, block_size_ * kDefaultBlockCount);
+    ASSERT_TRUE(utils::MakeTempFile("DeltaDiffUtilsTest-blob-XXXXXX",
+                                    &blob_path_,
+                                    &blob_fd_));
+  }
+
+  void TearDown() override {
+    unlink(old_part_.path.c_str());
+    unlink(new_part_.path.c_str());
+    if (blob_fd_ != -1)
+      close(blob_fd_);
+    unlink(blob_path_.c_str());
+  }
+
+  // Helper function to call DeltaMovedAndZeroBlocks() using this class' data
+  // members. This simply avoid repeating all the arguments that never change.
+  bool RunDeltaMovedAndZeroBlocks(ssize_t chunk_blocks,
+                                  bool src_ops_allowed) {
+    BlobFileWriter blob_file(blob_fd_, &blob_size_);
+    return diff_utils::DeltaMovedAndZeroBlocks(
+        &aops_,
+        old_part_.path,
+        new_part_.path,
+        old_part_.size / block_size_,
+        new_part_.size / block_size_,
+        chunk_blocks,
+        src_ops_allowed,
+        &blob_file,
+        &old_visited_blocks_,
+        &new_visited_blocks_);
+  }
+
+  // Old and new temporary partitions used in the tests. These are initialized
+  // with
+  PartitionConfig old_part_{"part"};
+  PartitionConfig new_part_{"part"};
+
+  // The file holding the output blob from the various diff utils functions.
+  string blob_path_;
+  int blob_fd_{-1};
+  off_t blob_size_{0};
+
+  size_t block_size_{kBlockSize};
+
+  // Default input/output arguments used when calling DeltaMovedAndZeroBlocks().
+  vector<AnnotatedOperation> aops_;
+  ExtentRanges old_visited_blocks_;
+  ExtentRanges new_visited_blocks_;
+};
+
+TEST_F(DeltaDiffUtilsTest, MoveSmallTest) {
+  brillo::Blob data_blob(block_size_);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(11, 1) };
+  vector<Extent> new_extents = { ExtentForRange(1, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      true,  // bsdiff_allowed
+      &data,
+      &op,
+      false));  // src_ops_allowed
+  EXPECT_TRUE(data.empty());
+
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::MOVE, op.type());
+  EXPECT_FALSE(op.has_data_offset());
+  EXPECT_FALSE(op.has_data_length());
+  EXPECT_EQ(1, op.src_extents_size());
+  EXPECT_EQ(kBlockSize, op.src_length());
+  EXPECT_EQ(1, op.dst_extents_size());
+  EXPECT_EQ(kBlockSize, op.dst_length());
+  EXPECT_EQ(BlocksInExtents(op.src_extents()),
+            BlocksInExtents(op.dst_extents()));
+  EXPECT_EQ(1, BlocksInExtents(op.dst_extents()));
+}
+
+TEST_F(DeltaDiffUtilsTest, MoveWithSameBlock) {
+  // Setup the old/new files so that it has immobile chunks; we make sure to
+  // utilize all sub-cases of such chunks: blocks 21--22 induce a split (src)
+  // and complete removal (dst), whereas blocks 24--25 induce trimming of the
+  // tail (src) and head (dst) of extents. The final block (29) is used for
+  // ensuring we properly account for the number of bytes removed in cases where
+  // the last block is partly filled. The detailed configuration:
+  //
+  // Old:  [ 20     21 22     23     24 25 ] [ 28     29 ]
+  // New:  [ 18 ] [ 21 22 ] [ 20 ] [ 24 25     26 ] [ 29 ]
+  // Same:          ^^ ^^            ^^ ^^            ^^
+  vector<Extent> old_extents = {
+      ExtentForRange(20, 6),
+      ExtentForRange(28, 2) };
+  vector<Extent> new_extents = {
+      ExtentForRange(18, 1),
+      ExtentForRange(21, 2),
+      ExtentForRange(20, 1),
+      ExtentForRange(24, 3),
+      ExtentForRange(29, 1) };
+
+  uint64_t num_blocks = BlocksInExtents(old_extents);
+  EXPECT_EQ(num_blocks, BlocksInExtents(new_extents));
+
+  // The size of the data should match the total number of blocks. Each block
+  // has a different content.
+  brillo::Blob file_data;
+  for (uint64_t i = 0; i < num_blocks; ++i) {
+    file_data.resize(file_data.size() + kBlockSize, 'a' + i);
+  }
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, file_data));
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, file_data));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      true,  // bsdiff_allowed
+      &data,
+      &op,
+      false));  // src_ops_allowed
+
+  EXPECT_TRUE(data.empty());
+
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::MOVE, op.type());
+  EXPECT_FALSE(op.has_data_offset());
+  EXPECT_FALSE(op.has_data_length());
+
+  // The expected old and new extents that actually moved. See comment above.
+  old_extents = {
+      ExtentForRange(20, 1),
+      ExtentForRange(23, 1),
+      ExtentForRange(28, 1) };
+  new_extents = {
+      ExtentForRange(18, 1),
+      ExtentForRange(20, 1),
+      ExtentForRange(26, 1) };
+  num_blocks = BlocksInExtents(old_extents);
+
+  EXPECT_EQ(num_blocks * kBlockSize, op.src_length());
+  EXPECT_EQ(num_blocks * kBlockSize, op.dst_length());
+
+  EXPECT_EQ(old_extents.size(), op.src_extents_size());
+  for (int i = 0; i < op.src_extents_size(); i++) {
+    EXPECT_EQ(old_extents[i].start_block(), op.src_extents(i).start_block())
+        << "i == " << i;
+    EXPECT_EQ(old_extents[i].num_blocks(), op.src_extents(i).num_blocks())
+        << "i == " << i;
+  }
+
+  EXPECT_EQ(new_extents.size(), op.dst_extents_size());
+  for (int i = 0; i < op.dst_extents_size(); i++) {
+    EXPECT_EQ(new_extents[i].start_block(), op.dst_extents(i).start_block())
+        << "i == " << i;
+    EXPECT_EQ(new_extents[i].num_blocks(), op.dst_extents(i).num_blocks())
+        << "i == " << i;
+  }
+}
+
+TEST_F(DeltaDiffUtilsTest, BsdiffSmallTest) {
+  // Test a BSDIFF operation from block 1 to block 2.
+  brillo::Blob data_blob(kBlockSize);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(1, 1) };
+  vector<Extent> new_extents = { ExtentForRange(2, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  // Modify one byte in the new file.
+  data_blob[0]++;
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      true,  // bsdiff_allowed
+      &data,
+      &op,
+      false));  // src_ops_allowed
+
+  EXPECT_FALSE(data.empty());
+
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::BSDIFF, op.type());
+  EXPECT_FALSE(op.has_data_offset());
+  EXPECT_FALSE(op.has_data_length());
+  EXPECT_EQ(1, op.src_extents_size());
+  EXPECT_EQ(kBlockSize, op.src_length());
+  EXPECT_EQ(1, op.dst_extents_size());
+  EXPECT_EQ(kBlockSize, op.dst_length());
+  EXPECT_EQ(BlocksInExtents(op.src_extents()),
+            BlocksInExtents(op.dst_extents()));
+  EXPECT_EQ(1, BlocksInExtents(op.dst_extents()));
+}
+
+TEST_F(DeltaDiffUtilsTest, BsdiffNotAllowedTest) {
+  // Same setup as the previous test, but this time BSDIFF operations are not
+  // allowed.
+  brillo::Blob data_blob(kBlockSize);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(1, 1) };
+  vector<Extent> new_extents = { ExtentForRange(2, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  // Modify one byte in the new file.
+  data_blob[0]++;
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      false,  // bsdiff_allowed
+      &data,
+      &op,
+      false));  // src_ops_allowed
+
+  EXPECT_FALSE(data.empty());
+
+  // The point of this test is that we don't use BSDIFF the way the above
+  // did. The rest of the details are to be caught in other tests.
+  EXPECT_TRUE(op.has_type());
+  EXPECT_NE(InstallOperation::BSDIFF, op.type());
+}
+
+TEST_F(DeltaDiffUtilsTest, BsdiffNotAllowedMoveTest) {
+  brillo::Blob data_blob(kBlockSize);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(1, 1) };
+  vector<Extent> new_extents = { ExtentForRange(2, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      false,  // bsdiff_allowed
+      &data,
+      &op,
+      false));  // src_ops_allowed
+
+  EXPECT_TRUE(data.empty());
+
+  // The point of this test is that we can still use a MOVE for a file
+  // that is blacklisted.
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::MOVE, op.type());
+}
+
+TEST_F(DeltaDiffUtilsTest, ReplaceSmallTest) {
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(1, 1) };
+  vector<Extent> new_extents = { ExtentForRange(2, 1) };
+
+  // Make a blob that's just 1's that will compress well.
+  brillo::Blob ones(kBlockSize, 1);
+
+  // Make a blob with random data that won't compress well.
+  brillo::Blob random_data;
+  std::mt19937 gen(12345);
+  std::uniform_int_distribution<uint8_t> dis(0, 255);
+  for (uint32_t i = 0; i < kBlockSize; i++) {
+    random_data.push_back(dis(gen));
+  }
+
+  for (int i = 0; i < 2; i++) {
+    brillo::Blob data_to_test = i == 0 ? random_data : ones;
+    // The old_extents will be initialized with 0.
+    EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize,
+                             data_to_test));
+
+    brillo::Blob data;
+    InstallOperation op;
+    EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+        old_part_.path,
+        new_part_.path,
+        old_extents,
+        new_extents,
+        true,  // bsdiff_allowed
+        &data,
+        &op,
+        false));  // src_ops_allowed
+    EXPECT_FALSE(data.empty());
+
+    EXPECT_TRUE(op.has_type());
+    const InstallOperation_Type expected_type =
+        (i == 0 ? InstallOperation::REPLACE : InstallOperation::REPLACE_BZ);
+    EXPECT_EQ(expected_type, op.type());
+    EXPECT_FALSE(op.has_data_offset());
+    EXPECT_FALSE(op.has_data_length());
+    EXPECT_EQ(0, op.src_extents_size());
+    EXPECT_FALSE(op.has_src_length());
+    EXPECT_EQ(1, op.dst_extents_size());
+    EXPECT_EQ(data_to_test.size(), op.dst_length());
+    EXPECT_EQ(1, BlocksInExtents(op.dst_extents()));
+  }
+}
+
+TEST_F(DeltaDiffUtilsTest, SourceCopyTest) {
+  // Makes sure SOURCE_COPY operations are emitted whenever src_ops_allowed
+  // is true. It is the same setup as MoveSmallTest, which checks that
+  // the operation is well-formed.
+  brillo::Blob data_blob(kBlockSize);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(11, 1) };
+  vector<Extent> new_extents = { ExtentForRange(1, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      true,  // bsdiff_allowed
+      &data,
+      &op,
+      true));  // src_ops_allowed
+  EXPECT_TRUE(data.empty());
+
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, op.type());
+}
+
+TEST_F(DeltaDiffUtilsTest, SourceBsdiffTest) {
+  // Makes sure SOURCE_BSDIFF operations are emitted whenever src_ops_allowed
+  // is true. It is the same setup as BsdiffSmallTest, which checks
+  // that the operation is well-formed.
+  brillo::Blob data_blob(kBlockSize);
+  test_utils::FillWithData(&data_blob);
+
+  // The old file is on a different block than the new one.
+  vector<Extent> old_extents = { ExtentForRange(1, 1) };
+  vector<Extent> new_extents = { ExtentForRange(2, 1) };
+
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_extents, kBlockSize, data_blob));
+  // Modify one byte in the new file.
+  data_blob[0]++;
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_extents, kBlockSize, data_blob));
+
+  brillo::Blob data;
+  InstallOperation op;
+  EXPECT_TRUE(diff_utils::ReadExtentsToDiff(
+      old_part_.path,
+      new_part_.path,
+      old_extents,
+      new_extents,
+      true,  // bsdiff_allowed
+      &data,
+      &op,
+      true));  // src_ops_allowed
+
+  EXPECT_FALSE(data.empty());
+  EXPECT_TRUE(op.has_type());
+  EXPECT_EQ(InstallOperation::SOURCE_BSDIFF, op.type());
+}
+
+TEST_F(DeltaDiffUtilsTest, IsNoopOperationTest) {
+  InstallOperation op;
+  op.set_type(InstallOperation::REPLACE_BZ);
+  EXPECT_FALSE(diff_utils::IsNoopOperation(op));
+  op.set_type(InstallOperation::MOVE);
+  EXPECT_TRUE(diff_utils::IsNoopOperation(op));
+  *(op.add_src_extents()) = ExtentForRange(3, 2);
+  *(op.add_dst_extents()) = ExtentForRange(3, 2);
+  EXPECT_TRUE(diff_utils::IsNoopOperation(op));
+  *(op.add_src_extents()) = ExtentForRange(7, 5);
+  *(op.add_dst_extents()) = ExtentForRange(7, 5);
+  EXPECT_TRUE(diff_utils::IsNoopOperation(op));
+  *(op.add_src_extents()) = ExtentForRange(20, 2);
+  *(op.add_dst_extents()) = ExtentForRange(20, 1);
+  *(op.add_dst_extents()) = ExtentForRange(21, 1);
+  EXPECT_TRUE(diff_utils::IsNoopOperation(op));
+  *(op.add_src_extents()) = ExtentForRange(24, 1);
+  *(op.add_dst_extents()) = ExtentForRange(25, 1);
+  EXPECT_FALSE(diff_utils::IsNoopOperation(op));
+}
+
+TEST_F(DeltaDiffUtilsTest, FilterNoopOperations) {
+  AnnotatedOperation aop1;
+  aop1.op.set_type(InstallOperation::REPLACE_BZ);
+  *(aop1.op.add_dst_extents()) = ExtentForRange(3, 2);
+  aop1.name = "aop1";
+
+  AnnotatedOperation aop2 = aop1;
+  aop2.name = "aop2";
+
+  AnnotatedOperation noop;
+  noop.op.set_type(InstallOperation::MOVE);
+  *(noop.op.add_src_extents()) = ExtentForRange(3, 2);
+  *(noop.op.add_dst_extents()) = ExtentForRange(3, 2);
+  noop.name = "noop";
+
+  vector<AnnotatedOperation> ops = {noop, aop1, noop, noop, aop2, noop};
+  diff_utils::FilterNoopOperations(&ops);
+  EXPECT_EQ(2u, ops.size());
+  EXPECT_EQ("aop1", ops[0].name);
+  EXPECT_EQ("aop2", ops[1].name);
+}
+
+// Test the simple case where all the blocks are different and no new blocks are
+// zeroed.
+TEST_F(DeltaDiffUtilsTest, NoZeroedOrUniqueBlocksDetected) {
+  InitializePartitionWithUniqueBlocks(old_part_, block_size_, 5);
+  InitializePartitionWithUniqueBlocks(new_part_, block_size_, 42);
+
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(-1,  // chunk_blocks
+                                         false));  // src_ops_allowed
+
+  EXPECT_EQ(0, old_visited_blocks_.blocks());
+  EXPECT_EQ(0, new_visited_blocks_.blocks());
+  EXPECT_EQ(0, blob_size_);
+  EXPECT_TRUE(aops_.empty());
+}
+
+// Test that when the partitions have identical blocks in the same positions no
+// MOVE operation is performed and all the blocks are handled.
+TEST_F(DeltaDiffUtilsTest, IdenticalPartitionsDontMove) {
+  InitializePartitionWithUniqueBlocks(old_part_, block_size_, 42);
+  InitializePartitionWithUniqueBlocks(new_part_, block_size_, 42);
+
+  // Mark some of the blocks as already visited.
+  vector<Extent> already_visited = {ExtentForRange(5, 10),
+                                    ExtentForRange(25, 10)};
+  old_visited_blocks_.AddExtents(already_visited);
+  new_visited_blocks_.AddExtents(already_visited);
+
+  // Most of the blocks rest in the same place, but there's no need for MOVE
+  // operations on those blocks.
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(-1,  // chunk_blocks
+                                         false));  // src_ops_allowed
+
+  EXPECT_EQ(kDefaultBlockCount, old_visited_blocks_.blocks());
+  EXPECT_EQ(kDefaultBlockCount, new_visited_blocks_.blocks());
+  EXPECT_EQ(0, blob_size_);
+  EXPECT_TRUE(aops_.empty());
+}
+
+// Test that when the partitions have identical blocks in the same positions
+// MOVE operation is performed and all the blocks are handled.
+TEST_F(DeltaDiffUtilsTest, IdenticalBlocksAreCopiedFromSource) {
+  // We use a smaller partition for this test.
+  old_part_.size = kBlockSize * 50;
+  new_part_.size = kBlockSize * 50;
+
+  InitializePartitionWithUniqueBlocks(old_part_, block_size_, 42);
+  InitializePartitionWithUniqueBlocks(new_part_, block_size_, 42);
+
+  // Mark some of the blocks as already visited.
+  vector<Extent> already_visited = {ExtentForRange(5, 5),
+                                    ExtentForRange(25, 7)};
+  old_visited_blocks_.AddExtents(already_visited);
+  new_visited_blocks_.AddExtents(already_visited);
+
+  // Override some of the old blocks with different data.
+  vector<Extent> different_blocks = {ExtentForRange(40, 5)};
+  EXPECT_TRUE(WriteExtents(old_part_.path, different_blocks, kBlockSize,
+                           brillo::Blob(5 * kBlockSize, 'a')));
+
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(10,  // chunk_blocks
+                                         true));  // src_ops_allowed
+
+  ExtentRanges expected_ranges;
+  expected_ranges.AddExtent(ExtentForRange(0, 50));
+  expected_ranges.SubtractExtents(different_blocks);
+
+  EXPECT_EQ(expected_ranges.extent_set(), old_visited_blocks_.extent_set());
+  EXPECT_EQ(expected_ranges.extent_set(), new_visited_blocks_.extent_set());
+  EXPECT_EQ(0, blob_size_);
+
+  // We expect all the blocks that we didn't override with |different_blocks|
+  // and that we didn't mark as visited in |already_visited| to match and have a
+  // SOURCE_COPY operation chunked at 10 blocks.
+  vector<Extent> expected_op_extents = {
+      ExtentForRange(0, 5),
+      ExtentForRange(10, 10),
+      ExtentForRange(20, 5),
+      ExtentForRange(32, 8),
+      ExtentForRange(45, 5),
+  };
+
+  EXPECT_EQ(expected_op_extents.size(), aops_.size());
+  for (size_t i = 0; i < aops_.size() && i < expected_op_extents.size(); ++i) {
+    SCOPED_TRACE(base::StringPrintf("Failed on operation number %" PRIuS, i));
+    const AnnotatedOperation& aop = aops_[i];
+    EXPECT_EQ(InstallOperation::SOURCE_COPY, aop.op.type());
+    EXPECT_EQ(1, aop.op.src_extents_size());
+    EXPECT_EQ(expected_op_extents[i], aop.op.src_extents(0));
+    EXPECT_EQ(1, aop.op.dst_extents_size());
+    EXPECT_EQ(expected_op_extents[i], aop.op.dst_extents(0));
+  }
+}
+
+TEST_F(DeltaDiffUtilsTest, IdenticalBlocksAreCopiedInOder) {
+  // We use a smaller partition for this test.
+  old_part_.size = block_size_ * 50;
+  new_part_.size = block_size_ * 50;
+
+  // Create two identical partitions with 5 copies of the same unique "file".
+  brillo::Blob file_data(block_size_ * 10, 'a');
+  for (size_t offset = 0; offset < file_data.size(); offset += block_size_)
+    file_data[offset] = 'a' + offset / block_size_;
+
+  brillo::Blob partition_data(old_part_.size);
+  for (size_t offset = 0; offset < partition_data.size();
+       offset += file_data.size()) {
+    std::copy(file_data.begin(), file_data.end(),
+              partition_data.begin() + offset);
+  }
+  EXPECT_TRUE(test_utils::WriteFileVector(old_part_.path, partition_data));
+  EXPECT_TRUE(test_utils::WriteFileVector(new_part_.path, partition_data));
+
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(-1,  // chunk_blocks
+                                         true));  // src_ops_allowed
+
+  // There should be only one SOURCE_COPY, for the whole partition and the
+  // source extents should cover only the first copy of the source file since
+  // we prefer to re-read files (maybe cached) instead of continue reading the
+  // rest of the partition.
+  EXPECT_EQ(1, aops_.size());
+  const AnnotatedOperation& aop = aops_[0];
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, aop.op.type());
+  EXPECT_EQ(5, aop.op.src_extents_size());
+  for (int i = 0; i < aop.op.src_extents_size(); ++i) {
+    EXPECT_EQ(ExtentForRange(0, 10), aop.op.src_extents(i));
+  }
+
+  EXPECT_EQ(1, aop.op.dst_extents_size());
+  EXPECT_EQ(ExtentForRange(0, 50), aop.op.dst_extents(0));
+
+  EXPECT_EQ(0, blob_size_);
+}
+
+// Test that all blocks with zeros are handled separately using REPLACE_BZ
+// operations unless they are not moved.
+TEST_F(DeltaDiffUtilsTest, ZeroBlocksUseReplaceBz) {
+  InitializePartitionWithUniqueBlocks(old_part_, block_size_, 42);
+  InitializePartitionWithUniqueBlocks(new_part_, block_size_, 5);
+
+  // We set four ranges of blocks with zeros: a single block, a range that fits
+  // in the chunk size, a range that doesn't and finally a range of zeros that
+  // was also zeros in the old image.
+  vector<Extent> new_zeros = {
+      ExtentForRange(10, 1),
+      ExtentForRange(20, 4),
+      // The last range is split since the old image has zeros in part of it.
+      ExtentForRange(30, 20),
+  };
+  brillo::Blob zeros_data(BlocksInExtents(new_zeros) * block_size_, '\0');
+  EXPECT_TRUE(WriteExtents(new_part_.path, new_zeros, block_size_, zeros_data));
+
+  vector<Extent> old_zeros = vector<Extent>{ExtentForRange(43, 7)};
+  EXPECT_TRUE(WriteExtents(old_part_.path, old_zeros, block_size_, zeros_data));
+
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(5,  // chunk_blocks
+                                         false));  // src_ops_allowed
+
+  // Zeroed blocks from old_visited_blocks_ were copied over, so me actually
+  // use them regardless of the trivial MOVE operation not being emitted.
+  EXPECT_EQ(old_zeros,
+            old_visited_blocks_.GetExtentsForBlockCount(
+                old_visited_blocks_.blocks()));
+
+  // All the new zeroed blocks should be used, part with REPLACE_BZ and part
+  // trivial MOVE operations (not included).
+  EXPECT_EQ(new_zeros,
+            new_visited_blocks_.GetExtentsForBlockCount(
+                new_visited_blocks_.blocks()));
+
+  vector<Extent> expected_op_extents = {
+      ExtentForRange(10, 1),
+      ExtentForRange(20, 4),
+      // This range should be split.
+      ExtentForRange(30, 5),
+      ExtentForRange(35, 5),
+      ExtentForRange(40, 3),
+  };
+
+  EXPECT_EQ(expected_op_extents.size(), aops_.size());
+  for (size_t i = 0; i < aops_.size() && i < expected_op_extents.size(); ++i) {
+    SCOPED_TRACE(base::StringPrintf("Failed on operation number %" PRIuS, i));
+    const AnnotatedOperation& aop = aops_[i];
+    EXPECT_EQ(InstallOperation::REPLACE_BZ, aop.op.type());
+    EXPECT_EQ(0, aop.op.src_extents_size());
+    EXPECT_EQ(1, aop.op.dst_extents_size());
+    EXPECT_EQ(expected_op_extents[i], aop.op.dst_extents(0));
+  }
+  EXPECT_NE(0, blob_size_);
+}
+
+TEST_F(DeltaDiffUtilsTest, ShuffledBlocksAreTracked) {
+  vector<uint64_t> permutation = {0, 1, 5, 6, 7, 2, 3, 4, 9, 10, 11, 12, 8};
+  vector<Extent> perm_extents;
+  for (uint64_t x : permutation)
+    AppendBlockToExtents(&perm_extents, x);
+
+  // We use a smaller partition for this test.
+  old_part_.size = block_size_ * permutation.size();
+  new_part_.size = block_size_ * permutation.size();
+  InitializePartitionWithUniqueBlocks(new_part_, block_size_, 123);
+
+  // We initialize the old_part_ with the blocks from new_part but in the
+  // |permutation| order. Block i in the old_part_ will contain the same data
+  // as block permutation[i] in the new_part_.
+  brillo::Blob new_contents;
+  EXPECT_TRUE(utils::ReadFile(new_part_.path, &new_contents));
+  EXPECT_TRUE(WriteExtents(old_part_.path, perm_extents, block_size_,
+                           new_contents));
+
+  EXPECT_TRUE(RunDeltaMovedAndZeroBlocks(-1,  // chunk_blocks
+                                         true));  // src_ops_allowed
+
+  EXPECT_EQ(permutation.size(), old_visited_blocks_.blocks());
+  EXPECT_EQ(permutation.size(), new_visited_blocks_.blocks());
+
+  // There should be only one SOURCE_COPY, with a complicate list of extents.
+  EXPECT_EQ(1, aops_.size());
+  const AnnotatedOperation& aop = aops_[0];
+  EXPECT_EQ(InstallOperation::SOURCE_COPY, aop.op.type());
+  vector<Extent> aop_src_extents;
+  ExtentsToVector(aop.op.src_extents(), &aop_src_extents);
+  EXPECT_EQ(perm_extents, aop_src_extents);
+
+  EXPECT_EQ(1, aop.op.dst_extents_size());
+  EXPECT_EQ(ExtentForRange(0, permutation.size()), aop.op.dst_extents(0));
+
+  EXPECT_EQ(0, blob_size_);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/ext2_filesystem.cc b/payload_generator/ext2_filesystem.cc
new file mode 100644
index 0000000..b452b41
--- /dev/null
+++ b/payload_generator/ext2_filesystem.cc
@@ -0,0 +1,355 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/ext2_filesystem.h"
+
+#include <et/com_err.h>
+#include <ext2fs/ext2_io.h>
+#include <ext2fs/ext2fs.h>
+
+#include <map>
+#include <set>
+
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/extent_utils.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::set;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+// Processes all blocks belonging to an inode and adds them to the extent list.
+// This function should match the prototype expected by ext2fs_block_iterate2().
+int ProcessInodeAllBlocks(ext2_filsys fs,
+                          blk_t* blocknr,
+                          e2_blkcnt_t blockcnt,
+                          blk_t ref_blk,
+                          int ref_offset,
+                          void* priv) {
+  vector<Extent>* extents = static_cast<vector<Extent>*>(priv);
+  AppendBlockToExtents(extents, *blocknr);
+  return 0;
+}
+
+// Processes only indirect, double indirect or triple indirect metadata
+// blocks belonging to an inode. This function should match the prototype of
+// ext2fs_block_iterate2().
+int AddMetadataBlocks(ext2_filsys fs,
+                      blk_t* blocknr,
+                      e2_blkcnt_t blockcnt,
+                      blk_t ref_blk,
+                      int ref_offset,
+                      void* priv) {
+  set<uint64_t>* blocks = static_cast<set<uint64_t>*>(priv);
+  // If |blockcnt| is non-negative, |blocknr| points to the physical block
+  // number.
+  // If |blockcnt| is negative, it is one of the values: BLOCK_COUNT_IND,
+  // BLOCK_COUNT_DIND, BLOCK_COUNT_TIND or BLOCK_COUNT_TRANSLATOR and
+  // |blocknr| points to a block in the first three cases. The last case is
+  // only used by GNU Hurd, so we shouldn't see those cases here.
+  if (blockcnt == BLOCK_COUNT_IND || blockcnt == BLOCK_COUNT_DIND ||
+      blockcnt == BLOCK_COUNT_TIND) {
+    blocks->insert(*blocknr);
+  }
+  return 0;
+}
+
+struct UpdateFileAndAppendState {
+  std::map<ext2_ino_t, FilesystemInterface::File>* inodes = nullptr;
+  set<ext2_ino_t>* used_inodes = nullptr;
+  vector<FilesystemInterface::File>* files = nullptr;
+  ext2_filsys filsys;
+};
+
+int UpdateFileAndAppend(ext2_ino_t dir,
+                        int entry,
+                        struct ext2_dir_entry *dirent,
+                        int offset,
+                        int blocksize,
+                        char *buf,
+                        void *priv_data) {
+  UpdateFileAndAppendState* state =
+      static_cast<UpdateFileAndAppendState*>(priv_data);
+  uint32_t file_type = dirent->name_len >> 8;
+  // Directories can't have hard links, and they are added from the outer loop.
+  if (file_type == EXT2_FT_DIR)
+    return 0;
+
+  auto ino_file = state->inodes->find(dirent->inode);
+  if (ino_file == state->inodes->end())
+    return 0;
+  auto dir_file = state->inodes->find(dir);
+  if (dir_file == state->inodes->end())
+    return 0;
+  string basename(dirent->name, dirent->name_len & 0xff);
+  ino_file->second.name = dir_file->second.name;
+  if (dir_file->second.name != "/")
+    ino_file->second.name += "/";
+  ino_file->second.name += basename;
+
+  // Append this file to the output. If the file has a hard link, it will be
+  // added twice to the output, but with different names, which is ok. That will
+  // help identify all the versions of the same file.
+  state->files->push_back(ino_file->second);
+  state->used_inodes->insert(dirent->inode);
+  return 0;
+}
+
+}  // namespace
+
+unique_ptr<Ext2Filesystem> Ext2Filesystem::CreateFromFile(
+    const string& filename) {
+  if (filename.empty())
+    return nullptr;
+  unique_ptr<Ext2Filesystem> result(new Ext2Filesystem());
+  result->filename_ = filename;
+
+  errcode_t err = ext2fs_open(filename.c_str(),
+                              0,  // flags (read only)
+                              0,  // superblock block number
+                              0,  // block_size (autodetect)
+                              unix_io_manager,
+                              &result->filsys_);
+  if (err) {
+    LOG(ERROR) << "Opening ext2fs " << filename;
+    return nullptr;
+  }
+  return result;
+}
+
+Ext2Filesystem::~Ext2Filesystem() {
+  ext2fs_free(filsys_);
+}
+
+size_t Ext2Filesystem::GetBlockSize() const {
+  return filsys_->blocksize;
+}
+
+size_t Ext2Filesystem::GetBlockCount() const {
+  return ext2fs_blocks_count(filsys_->super);
+}
+
+bool Ext2Filesystem::GetFiles(vector<File>* files) const {
+  TEST_AND_RETURN_FALSE_ERRCODE(ext2fs_read_inode_bitmap(filsys_));
+
+  ext2_inode_scan iscan;
+  TEST_AND_RETURN_FALSE_ERRCODE(
+      ext2fs_open_inode_scan(filsys_, 0 /* buffer_blocks */, &iscan));
+
+  std::map<ext2_ino_t, File> inodes;
+
+  // List of directories. We need to first parse all the files in a directory
+  // to later fix the absolute paths.
+  vector<ext2_ino_t> directories;
+
+  set<uint64_t> inode_blocks;
+
+  // Iterator
+  ext2_ino_t it_ino;
+  ext2_inode it_inode;
+
+  bool ok = true;
+  while (true) {
+    errcode_t error = ext2fs_get_next_inode(iscan, &it_ino, &it_inode);
+    if (error) {
+      LOG(ERROR) << "Failed to retrieve next inode (" << error << ")";
+      ok = false;
+      break;
+    }
+    if (it_ino == 0)
+      break;
+
+    // Skip inodes that are not in use.
+    if (!ext2fs_test_inode_bitmap(filsys_->inode_map, it_ino))
+      continue;
+
+    File& file = inodes[it_ino];
+    if (it_ino == EXT2_RESIZE_INO) {
+      file.name = "<group-descriptors>";
+    } else {
+      file.name = base::StringPrintf("<inode-%u>", it_ino);
+    }
+
+    memset(&file.file_stat, 0, sizeof(file.file_stat));
+    file.file_stat.st_ino = it_ino;
+    file.file_stat.st_mode = it_inode.i_mode;
+    file.file_stat.st_nlink = it_inode.i_links_count;
+    file.file_stat.st_uid = it_inode.i_uid;
+    file.file_stat.st_gid = it_inode.i_gid;
+    file.file_stat.st_size = it_inode.i_size;
+    file.file_stat.st_blksize = filsys_->blocksize;
+    file.file_stat.st_blocks = it_inode.i_blocks;
+    file.file_stat.st_atime = it_inode.i_atime;
+    file.file_stat.st_mtime = it_inode.i_mtime;
+    file.file_stat.st_ctime = it_inode.i_ctime;
+
+    bool is_dir = (ext2fs_check_directory(filsys_, it_ino) == 0);
+    if (is_dir)
+      directories.push_back(it_ino);
+
+    if (!ext2fs_inode_has_valid_blocks(&it_inode))
+      continue;
+
+    // Process the inode data and metadata blocks.
+    // For normal files, inode blocks are indirect, double indirect
+    // and triple indirect blocks (no data blocks). For directories and
+    // the journal, all blocks are considered metadata blocks.
+    int flags = it_ino < EXT2_GOOD_OLD_FIRST_INO ? 0 : BLOCK_FLAG_DATA_ONLY;
+    error = ext2fs_block_iterate2(filsys_, it_ino, flags,
+                                  nullptr,  // block_buf
+                                  ProcessInodeAllBlocks,
+                                  &file.extents);
+
+    if (error) {
+      LOG(ERROR) << "Failed to enumerate inode " << it_ino
+                << " blocks (" << error << ")";
+      continue;
+    }
+    if (it_ino >= EXT2_GOOD_OLD_FIRST_INO) {
+      ext2fs_block_iterate2(filsys_, it_ino, 0, nullptr,
+                            AddMetadataBlocks,
+                            &inode_blocks);
+    }
+  }
+  ext2fs_close_inode_scan(iscan);
+  if (!ok)
+    return false;
+
+  // The set of inodes already added to the output. There can be less elements
+  // here than in files since the later can contain repeated inodes due to
+  // hardlink files.
+  set<ext2_ino_t> used_inodes;
+
+  UpdateFileAndAppendState priv_data;
+  priv_data.inodes = &inodes;
+  priv_data.used_inodes = &used_inodes;
+  priv_data.files = files;
+  priv_data.filsys = filsys_;
+
+  files->clear();
+  // Iterate over all the files of each directory to update the name and add it.
+  for (ext2_ino_t dir_ino : directories) {
+    char* dir_name = nullptr;
+    errcode_t error = ext2fs_get_pathname(filsys_, dir_ino, 0, &dir_name);
+    if (error) {
+      // Not being able to read a directory name is not a fatal error, it is
+      // just skiped.
+      LOG(WARNING) << "Reading directory name on inode " << dir_ino
+                   << " (error " << error << ")";
+      inodes[dir_ino].name = base::StringPrintf("<dir-%u>", dir_ino);
+    } else {
+      inodes[dir_ino].name = dir_name;
+      files->push_back(inodes[dir_ino]);
+      used_inodes.insert(dir_ino);
+    }
+    ext2fs_free_mem(&dir_name);
+
+    error = ext2fs_dir_iterate2(
+        filsys_, dir_ino, 0, nullptr /* block_buf */,
+        UpdateFileAndAppend, &priv_data);
+    if (error) {
+      LOG(WARNING) << "Failed to enumerate files in directory "
+                   << inodes[dir_ino].name << " (error " << error << ")";
+    }
+  }
+
+  // Add <inode-blocks> file with the blocks that hold inodes.
+  File inode_file;
+  inode_file.name = "<inode-blocks>";
+  for (uint64_t block : inode_blocks) {
+    AppendBlockToExtents(&inode_file.extents, block);
+  }
+  files->push_back(inode_file);
+
+  // Add <free-spacce> blocs.
+  errcode_t error = ext2fs_read_block_bitmap(filsys_);
+  if (error) {
+    LOG(ERROR) << "Reading the blocks bitmap (error " << error << ")";
+  } else {
+    File free_space;
+    free_space.name = "<free-space>";
+    blk64_t blk_start = ext2fs_get_block_bitmap_start2(filsys_->block_map);
+    blk64_t blk_end = ext2fs_get_block_bitmap_end2(filsys_->block_map);
+    for (blk64_t block = blk_start; block < blk_end; block++) {
+      if (!ext2fs_test_block_bitmap2(filsys_->block_map, block))
+        AppendBlockToExtents(&free_space.extents, block);
+    }
+    files->push_back(free_space);
+  }
+
+  // Add all the unreachable files plus the pseudo-files with an inode. Since
+  // these inodes aren't files in the filesystem, ignore the empty ones.
+  for (const auto& ino_file : inodes) {
+    if (used_inodes.find(ino_file.first) != used_inodes.end())
+      continue;
+    if (ino_file.second.extents.empty())
+      continue;
+
+    File file = ino_file.second;
+    ExtentRanges ranges;
+    ranges.AddExtents(file.extents);
+    file.extents = ranges.GetExtentsForBlockCount(ranges.blocks());
+
+    files->push_back(file);
+  }
+
+  return true;
+}
+
+bool Ext2Filesystem::LoadSettings(brillo::KeyValueStore* store) const {
+  // First search for the settings inode following symlinks if we find some.
+  ext2_ino_t ino_num = 0;
+  errcode_t err = ext2fs_namei_follow(
+      filsys_, EXT2_ROOT_INO /* root */, EXT2_ROOT_INO /* cwd */,
+      "/etc/update_engine.conf", &ino_num);
+  if (err != 0)
+    return false;
+
+  ext2_inode ino_data;
+  if (ext2fs_read_inode(filsys_, ino_num, &ino_data) != 0)
+    return false;
+
+  // Load the list of blocks and then the contents of the inodes.
+  vector<Extent> extents;
+  err = ext2fs_block_iterate2(filsys_, ino_num, BLOCK_FLAG_DATA_ONLY,
+                              nullptr,  // block_buf
+                              ProcessInodeAllBlocks,
+                              &extents);
+  if (err != 0)
+    return false;
+
+  brillo::Blob blob;
+  uint64_t physical_size = BlocksInExtents(extents) * filsys_->blocksize;
+  // Sparse holes in the settings file are not supported.
+  if (EXT2_I_SIZE(&ino_data) > physical_size)
+    return false;
+  if (!utils::ReadExtents(filename_, extents, &blob, physical_size,
+                          filsys_->blocksize))
+    return false;
+
+  string text(blob.begin(), blob.begin() + EXT2_I_SIZE(&ino_data));
+  return store->LoadFromString(text);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/ext2_filesystem.h b/payload_generator/ext2_filesystem.h
new file mode 100644
index 0000000..248e208
--- /dev/null
+++ b/payload_generator/ext2_filesystem.h
@@ -0,0 +1,71 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_EXT2_FILESYSTEM_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_EXT2_FILESYSTEM_H_
+
+#include "update_engine/payload_generator/filesystem_interface.h"
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <ext2fs/ext2fs.h>
+
+namespace chromeos_update_engine {
+
+class Ext2Filesystem : public FilesystemInterface {
+ public:
+  // Creates an Ext2Filesystem from a ext2 formatted filesystem stored in a
+  // file. The file doesn't need to be loop-back mounted.
+  static std::unique_ptr<Ext2Filesystem> CreateFromFile(
+      const std::string& filename);
+  virtual ~Ext2Filesystem();
+
+  // FilesystemInterface overrides.
+  size_t GetBlockSize() const override;
+  size_t GetBlockCount() const override;
+
+  // GetFiles will return one FilesystemInterface::File for every file and every
+  // directory in the filesystem. Hard-linked files will appear in the list
+  // several times with the same list of blocks.
+  // On addition to actual files, it also returns these pseudo-files:
+  //  <free-space>: With all the unallocated data-blocks.
+  //  <inode-blocks>: Will all the data-blocks for second and third level inodes
+  //    of all the files.
+  //  <group-descriptors>: With the block group descriptor and their reserved
+  //    space.
+  //  <metadata>: With the rest of ext2 metadata blocks, such as superblocks
+  //    and bitmap tables.
+  bool GetFiles(std::vector<File>* files) const override;
+
+  bool LoadSettings(brillo::KeyValueStore* store) const override;
+
+ private:
+  Ext2Filesystem() = default;
+
+  // The ext2 main data structure holding the filesystem.
+  ext2_filsys filsys_ = nullptr;
+
+  // The file where the filesystem is stored.
+  std::string filename_;
+
+  DISALLOW_COPY_AND_ASSIGN(Ext2Filesystem);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_EXT2_FILESYSTEM_H_
diff --git a/payload_generator/ext2_filesystem_unittest.cc b/payload_generator/ext2_filesystem_unittest.cc
new file mode 100644
index 0000000..df8b98f
--- /dev/null
+++ b/payload_generator/ext2_filesystem_unittest.cc
@@ -0,0 +1,214 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/ext2_filesystem.h"
+
+#include <unistd.h>
+
+#include <map>
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/format_macros.h>
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using chromeos_update_engine::test_utils::System;
+using std::map;
+using std::set;
+using std::string;
+using std::unique_ptr;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+uint64_t kDefaultFilesystemSize = 4 * 1024 * 1024;
+size_t kDefaultFilesystemBlockCount = 1024;
+size_t kDefaultFilesystemBlockSize = 4096;
+
+// Checks that all the blocks in |extents| are in the range [0, total_blocks).
+void ExpectBlocksInRange(const vector<Extent>& extents, uint64_t total_blocks) {
+  for (const Extent& extent : extents) {
+    EXPECT_LE(0, extent.start_block());
+    EXPECT_LE(extent.start_block() + extent.num_blocks(), total_blocks);
+  }
+}
+
+}  // namespace
+
+
+class Ext2FilesystemTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    ASSERT_TRUE(utils::MakeTempFile("Ext2FilesystemTest-XXXXXX",
+                                    &fs_filename_, nullptr));
+    ASSERT_EQ(0, truncate(fs_filename_.c_str(), kDefaultFilesystemSize));
+  }
+
+  void TearDown() override {
+    unlink(fs_filename_.c_str());
+  }
+
+  string fs_filename_;
+};
+
+TEST_F(Ext2FilesystemTest, InvalidFilesystem) {
+  unique_ptr<Ext2Filesystem> fs = Ext2Filesystem::CreateFromFile(fs_filename_);
+  ASSERT_EQ(nullptr, fs.get());
+
+  fs = Ext2Filesystem::CreateFromFile("/path/to/invalid/file");
+  ASSERT_EQ(nullptr, fs.get());
+}
+
+TEST_F(Ext2FilesystemTest, EmptyFilesystem) {
+  EXPECT_EQ(0, System(base::StringPrintf(
+      "/sbin/mkfs.ext2 -q -b %" PRIuS " -F %s",
+      kDefaultFilesystemBlockSize, fs_filename_.c_str())));
+  unique_ptr<Ext2Filesystem> fs = Ext2Filesystem::CreateFromFile(fs_filename_);
+
+  ASSERT_NE(nullptr, fs.get());
+  EXPECT_EQ(kDefaultFilesystemBlockCount, fs->GetBlockCount());
+  EXPECT_EQ(kDefaultFilesystemBlockSize, fs->GetBlockSize());
+
+  vector<FilesystemInterface::File> files;
+  EXPECT_TRUE(fs->GetFiles(&files));
+
+  map<string, FilesystemInterface::File> map_files;
+  for (const auto& file : files) {
+    EXPECT_EQ(map_files.end(), map_files.find(file.name))
+        << "File " << file.name << " repeated in the list.";
+    map_files[file.name] = file;
+    ExpectBlocksInRange(file.extents, fs->GetBlockCount());
+  }
+  EXPECT_EQ(2, map_files["/"].file_stat.st_ino);
+  EXPECT_FALSE(map_files["<free-space>"].extents.empty());
+}
+
+// This test parses the sample images generated during build time with the
+// "generate_image.sh" script. The expected conditions of each file in these
+// images is encoded in the file name, as defined in the mentioned script.
+TEST_F(Ext2FilesystemTest, ParseGeneratedImages) {
+  const vector<string> kGeneratedImages = {
+      "disk_ext2_1k.img",
+      "disk_ext2_4k.img" };
+  base::FilePath build_path = test_utils::GetBuildArtifactsPath().Append("gen");
+  for (const string& fs_name : kGeneratedImages) {
+    LOG(INFO) << "Testing " << fs_name;
+    unique_ptr<Ext2Filesystem> fs = Ext2Filesystem::CreateFromFile(
+        build_path.Append(fs_name).value());
+    ASSERT_NE(nullptr, fs.get());
+
+    vector<FilesystemInterface::File> files;
+    map<string, FilesystemInterface::File> map_files;
+    set<string> filenames;
+    EXPECT_TRUE(fs->GetFiles(&files));
+    for (const auto& file : files) {
+      // Check no repeated files. We should parse hard-links with two different
+      // names.
+      EXPECT_EQ(map_files.end(), map_files.find(file.name))
+          << "File " << file.name << " repeated in the list.";
+      map_files[file.name] = file;
+      filenames.insert(file.name);
+      ExpectBlocksInRange(file.extents, fs->GetBlockCount());
+    }
+
+    // Check that all the files are parsed, and the /removed file should not
+    // be included in the list.
+    set<string> kExpectedFiles = {
+        "/",
+        "/dir1",
+        "/dir1/file",
+        "/dir1/dir2",
+        "/dir1/dir2/file",
+        "/dir1/dir2/dir1",
+        "/empty-file",
+        "/link-hard-regular-16k",
+        "/link-long_symlink",
+        "/link-short_symlink",
+        "/lost+found",
+        "/regular-small",
+        "/regular-16k",
+        "/regular-32k-zeros",
+        "/regular-with_net_cap",
+        "/sparse_empty-10k",
+        "/sparse_empty-2blocks",
+        "/sparse-10000blocks",
+        "/sparse-16k-last_block",
+        "/sparse-16k-first_block",
+        "/sparse-16k-holes",
+        "<inode-blocks>",
+        "<free-space>",
+        "<group-descriptors>",
+    };
+    EXPECT_EQ(kExpectedFiles, filenames);
+
+    FilesystemInterface::File file;
+
+    // Small symlinks don't actually have data blocks.
+    EXPECT_TRUE(map_files["/link-short_symlink"].extents.empty());
+    EXPECT_EQ(1, BlocksInExtents(map_files["/link-long_symlink"].extents));
+
+    // Hard-links report the same list of blocks.
+    EXPECT_EQ(map_files["/link-hard-regular-16k"].extents,
+              map_files["/regular-16k"].extents);
+    EXPECT_FALSE(map_files["/regular-16k"].extents.empty());
+
+    // The number of blocks in these files doesn't depend on the
+    // block size.
+    EXPECT_TRUE(map_files["/empty-file"].extents.empty());
+    EXPECT_EQ(1, BlocksInExtents(map_files["/regular-small"].extents));
+    EXPECT_EQ(1, BlocksInExtents(map_files["/regular-with_net_cap"].extents));
+    EXPECT_TRUE(map_files["/sparse_empty-10k"].extents.empty());
+    EXPECT_TRUE(map_files["/sparse_empty-2blocks"].extents.empty());
+    EXPECT_EQ(1, BlocksInExtents(map_files["/sparse-16k-last_block"].extents));
+    EXPECT_EQ(1, BlocksInExtents(map_files["/sparse-16k-first_block"].extents));
+    EXPECT_EQ(2, BlocksInExtents(map_files["/sparse-16k-holes"].extents));
+  }
+}
+
+TEST_F(Ext2FilesystemTest, LoadSettingsFailsTest) {
+  base::FilePath path = test_utils::GetBuildArtifactsPath().Append(
+      "gen/disk_ext2_1k.img");
+  unique_ptr<Ext2Filesystem> fs = Ext2Filesystem::CreateFromFile(path.value());
+
+  brillo::KeyValueStore store;
+  // disk_ext2_1k.img doesn't have the /etc/update_engine.conf file.
+  EXPECT_FALSE(fs->LoadSettings(&store));
+}
+
+TEST_F(Ext2FilesystemTest, LoadSettingsWorksTest) {
+  base::FilePath path = test_utils::GetBuildArtifactsPath().Append(
+      "gen/disk_ext2_ue_settings.img");
+  unique_ptr<Ext2Filesystem> fs = Ext2Filesystem::CreateFromFile(path.value());
+
+  brillo::KeyValueStore store;
+  EXPECT_TRUE(fs->LoadSettings(&store));
+  string minor_version;
+  EXPECT_TRUE(store.GetString("PAYLOAD_MINOR_VERSION", &minor_version));
+  EXPECT_EQ("1234", minor_version);
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/extent_ranges.cc b/payload_generator/extent_ranges.cc
new file mode 100644
index 0000000..848fdc7
--- /dev/null
+++ b/payload_generator/extent_ranges.cc
@@ -0,0 +1,306 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/extent_ranges.h"
+
+#include <algorithm>
+#include <set>
+#include <utility>
+#include <vector>
+
+#include <base/logging.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+
+using std::set;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+bool ExtentRanges::ExtentsOverlapOrTouch(const Extent& a, const Extent& b) {
+  if (a.start_block() == b.start_block())
+    return true;
+  if (a.start_block() == kSparseHole || b.start_block() == kSparseHole)
+    return false;
+  if (a.start_block() < b.start_block()) {
+    return a.start_block() + a.num_blocks() >= b.start_block();
+  } else {
+    return b.start_block() + b.num_blocks() >= a.start_block();
+  }
+}
+
+bool ExtentRanges::ExtentsOverlap(const Extent& a, const Extent& b) {
+  if (a.start_block() == b.start_block())
+    return true;
+  if (a.start_block() == kSparseHole || b.start_block() == kSparseHole)
+    return false;
+  if (a.start_block() < b.start_block()) {
+    return a.start_block() + a.num_blocks() > b.start_block();
+  } else {
+    return b.start_block() + b.num_blocks() > a.start_block();
+  }
+}
+
+void ExtentRanges::AddBlock(uint64_t block) {
+  AddExtent(ExtentForRange(block, 1));
+}
+
+void ExtentRanges::SubtractBlock(uint64_t block) {
+  SubtractExtent(ExtentForRange(block, 1));
+}
+
+namespace {
+
+Extent UnionOverlappingExtents(const Extent& first, const Extent& second) {
+  CHECK_NE(kSparseHole, first.start_block());
+  CHECK_NE(kSparseHole, second.start_block());
+  uint64_t start = std::min(first.start_block(), second.start_block());
+  uint64_t end = std::max(first.start_block() + first.num_blocks(),
+                          second.start_block() + second.num_blocks());
+  return ExtentForRange(start, end - start);
+}
+
+}  // namespace
+
+void ExtentRanges::AddExtent(Extent extent) {
+  if (extent.start_block() == kSparseHole || extent.num_blocks() == 0)
+    return;
+
+  ExtentSet::iterator begin_del = extent_set_.end();
+  ExtentSet::iterator end_del = extent_set_.end();
+  uint64_t del_blocks = 0;
+  for (ExtentSet::iterator it = extent_set_.begin(), e = extent_set_.end();
+       it != e; ++it) {
+    if (ExtentsOverlapOrTouch(*it, extent)) {
+      end_del = it;
+      ++end_del;
+      del_blocks += it->num_blocks();
+      if (begin_del == extent_set_.end())
+        begin_del = it;
+
+      extent = UnionOverlappingExtents(extent, *it);
+    }
+  }
+  extent_set_.erase(begin_del, end_del);
+  extent_set_.insert(extent);
+  blocks_ -= del_blocks;
+  blocks_ += extent.num_blocks();
+}
+
+namespace {
+// Returns base - subtractee (set subtraction).
+ExtentRanges::ExtentSet SubtractOverlappingExtents(const Extent& base,
+                                                   const Extent& subtractee) {
+  ExtentRanges::ExtentSet ret;
+  if (subtractee.start_block() > base.start_block()) {
+    ret.insert(ExtentForRange(base.start_block(),
+                              subtractee.start_block() - base.start_block()));
+  }
+  uint64_t base_end = base.start_block() + base.num_blocks();
+  uint64_t subtractee_end = subtractee.start_block() + subtractee.num_blocks();
+  if (base_end > subtractee_end) {
+    ret.insert(ExtentForRange(subtractee_end, base_end - subtractee_end));
+  }
+  return ret;
+}
+}  // namespace
+
+void ExtentRanges::SubtractExtent(const Extent& extent) {
+  if (extent.start_block() == kSparseHole || extent.num_blocks() == 0)
+    return;
+
+  ExtentSet::iterator begin_del = extent_set_.end();
+  ExtentSet::iterator end_del = extent_set_.end();
+  uint64_t del_blocks = 0;
+  ExtentSet new_extents;
+  for (ExtentSet::iterator it = extent_set_.begin(), e = extent_set_.end();
+       it != e; ++it) {
+    if (!ExtentsOverlap(*it, extent))
+      continue;
+
+    if (begin_del == extent_set_.end())
+      begin_del = it;
+    end_del = it;
+    ++end_del;
+
+    del_blocks += it->num_blocks();
+
+    ExtentSet subtraction = SubtractOverlappingExtents(*it, extent);
+    for (ExtentSet::iterator jt = subtraction.begin(), je = subtraction.end();
+         jt != je; ++jt) {
+      new_extents.insert(*jt);
+      del_blocks -= jt->num_blocks();
+    }
+  }
+  extent_set_.erase(begin_del, end_del);
+  extent_set_.insert(new_extents.begin(), new_extents.end());
+  blocks_ -= del_blocks;
+}
+
+void ExtentRanges::AddRanges(const ExtentRanges& ranges) {
+  for (ExtentSet::const_iterator it = ranges.extent_set_.begin(),
+           e = ranges.extent_set_.end(); it != e; ++it) {
+    AddExtent(*it);
+  }
+}
+
+void ExtentRanges::SubtractRanges(const ExtentRanges& ranges) {
+  for (ExtentSet::const_iterator it = ranges.extent_set_.begin(),
+           e = ranges.extent_set_.end(); it != e; ++it) {
+    SubtractExtent(*it);
+  }
+}
+
+void ExtentRanges::AddExtents(const vector<Extent>& extents) {
+  for (vector<Extent>::const_iterator it = extents.begin(), e = extents.end();
+       it != e; ++it) {
+    AddExtent(*it);
+  }
+}
+
+void ExtentRanges::SubtractExtents(const vector<Extent>& extents) {
+  for (vector<Extent>::const_iterator it = extents.begin(), e = extents.end();
+       it != e; ++it) {
+    SubtractExtent(*it);
+  }
+}
+
+void ExtentRanges::AddRepeatedExtents(
+    const ::google::protobuf::RepeatedPtrField<Extent> &exts) {
+  for (int i = 0, e = exts.size(); i != e; ++i) {
+    AddExtent(exts.Get(i));
+  }
+}
+
+void ExtentRanges::SubtractRepeatedExtents(
+    const ::google::protobuf::RepeatedPtrField<Extent> &exts) {
+  for (int i = 0, e = exts.size(); i != e; ++i) {
+    SubtractExtent(exts.Get(i));
+  }
+}
+
+bool ExtentRanges::ContainsBlock(uint64_t block) const {
+  auto lower = extent_set_.lower_bound(ExtentForRange(block, 1));
+  // The block could be on the extent before the one in |lower|.
+  if (lower != extent_set_.begin())
+    lower--;
+  // Any extent starting at block+1 or later is not interesting, so this is the
+  // upper limit.
+  auto upper = extent_set_.lower_bound(ExtentForRange(block + 1, 0));
+  for (auto iter = lower; iter != upper; ++iter) {
+    if (iter->start_block() <= block &&
+        block < iter->start_block() + iter->num_blocks()) {
+      return true;
+    }
+  }
+  return false;
+}
+
+void ExtentRanges::Dump() const {
+  LOG(INFO) << "ExtentRanges Dump. blocks: " << blocks_;
+  for (ExtentSet::const_iterator it = extent_set_.begin(),
+           e = extent_set_.end();
+       it != e; ++it) {
+    LOG(INFO) << "{" << it->start_block() << ", " << it->num_blocks() << "}";
+  }
+}
+
+Extent ExtentForRange(uint64_t start_block, uint64_t num_blocks) {
+  Extent ret;
+  ret.set_start_block(start_block);
+  ret.set_num_blocks(num_blocks);
+  return ret;
+}
+
+vector<Extent> ExtentRanges::GetExtentsForBlockCount(
+    uint64_t count) const {
+  vector<Extent> out;
+  if (count == 0)
+    return out;
+  uint64_t out_blocks = 0;
+  CHECK(count <= blocks_);
+  for (ExtentSet::const_iterator it = extent_set_.begin(),
+           e = extent_set_.end();
+       it != e; ++it) {
+    const uint64_t blocks_needed = count - out_blocks;
+    const Extent& extent = *it;
+    out.push_back(extent);
+    out_blocks += extent.num_blocks();
+    if (extent.num_blocks() < blocks_needed)
+      continue;
+    if (extent.num_blocks() == blocks_needed)
+      break;
+    // If we get here, we just added the last extent needed, but it's too big
+    out_blocks -= extent.num_blocks();
+    out_blocks += blocks_needed;
+    out.back().set_num_blocks(blocks_needed);
+    break;
+  }
+  return out;
+}
+
+vector<Extent> FilterExtentRanges(const vector<Extent>& extents,
+                                  const ExtentRanges& ranges) {
+  vector<Extent> result;
+  const ExtentRanges::ExtentSet& extent_set = ranges.extent_set();
+  for (Extent extent : extents) {
+    // The extents are sorted by the start_block. We want to iterate all the
+    // Extents in the ExtentSet possibly overlapping the current |extent|. This
+    // is achieved by looking from the extent whose start_block is *lower* than
+    // the extent.start_block() up to the greatest extent whose start_block is
+    // lower than extent.start_block() + extent.num_blocks().
+    auto lower = extent_set.lower_bound(extent);
+    // We need to decrement the lower_bound to look at the extent that could
+    // overlap the beginning of the current |extent|.
+    if (lower != extent_set.begin())
+      lower--;
+    auto upper = extent_set.lower_bound(
+        ExtentForRange(extent.start_block() + extent.num_blocks(), 0));
+    for (auto iter = lower; iter != upper; ++iter) {
+      if (!ExtentRanges::ExtentsOverlap(extent, *iter))
+        continue;
+      if (iter->start_block() <= extent.start_block()) {
+        // We need to cut blocks from the beginning of the |extent|.
+        uint64_t cut_blocks = iter->start_block() + iter->num_blocks() -
+            extent.start_block();
+        if (cut_blocks >= extent.num_blocks()) {
+          extent.set_num_blocks(0);
+          break;
+        }
+        extent = ExtentForRange(extent.start_block() + cut_blocks,
+                                extent.num_blocks() - cut_blocks);
+      } else {
+        // We need to cut blocks on the middle of the extent, possible up to the
+        // end of it.
+        result.push_back(
+            ExtentForRange(extent.start_block(),
+                           iter->start_block() - extent.start_block()));
+        uint64_t new_start = iter->start_block() + iter->num_blocks();
+        uint64_t old_end = extent.start_block() + extent.num_blocks();
+        if (new_start >= old_end) {
+          extent.set_num_blocks(0);
+          break;
+        }
+        extent = ExtentForRange(new_start, old_end - new_start);
+      }
+    }
+    if (extent.num_blocks() > 0)
+      result.push_back(extent);
+  }
+  return result;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/extent_ranges.h b/payload_generator/extent_ranges.h
new file mode 100644
index 0000000..198c834
--- /dev/null
+++ b/payload_generator/extent_ranges.h
@@ -0,0 +1,94 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_RANGES_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_RANGES_H_
+
+#include <map>
+#include <set>
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/update_metadata.pb.h"
+
+// An ExtentRanges object represents an unordered collection of extents (and
+// therefore blocks). Such an object may be modified by adding or subtracting
+// blocks (think: set addition or set subtraction). Note that ExtentRanges
+// ignores sparse hole extents mostly to avoid confusion between extending a
+// sparse hole range vs. set addition but also to ensure that the delta
+// generator doesn't use sparse holes as scratch space.
+
+namespace chromeos_update_engine {
+
+struct ExtentLess {
+  bool operator()(const Extent& x, const Extent& y) const {
+    return x.start_block() < y.start_block();
+  }
+};
+
+Extent ExtentForRange(uint64_t start_block, uint64_t num_blocks);
+
+class ExtentRanges {
+ public:
+  typedef std::set<Extent, ExtentLess> ExtentSet;
+
+  ExtentRanges() : blocks_(0) {}
+  void AddBlock(uint64_t block);
+  void SubtractBlock(uint64_t block);
+  void AddExtent(Extent extent);
+  void SubtractExtent(const Extent& extent);
+  void AddExtents(const std::vector<Extent>& extents);
+  void SubtractExtents(const std::vector<Extent>& extents);
+  void AddRepeatedExtents(
+      const ::google::protobuf::RepeatedPtrField<Extent> &exts);
+  void SubtractRepeatedExtents(
+      const ::google::protobuf::RepeatedPtrField<Extent> &exts);
+  void AddRanges(const ExtentRanges& ranges);
+  void SubtractRanges(const ExtentRanges& ranges);
+
+  // Returns whether the block |block| is in this ExtentRange.
+  bool ContainsBlock(uint64_t block) const;
+
+  static bool ExtentsOverlapOrTouch(const Extent& a, const Extent& b);
+  static bool ExtentsOverlap(const Extent& a, const Extent& b);
+
+  // Dumps contents to the log file. Useful for debugging.
+  void Dump() const;
+
+  uint64_t blocks() const { return blocks_; }
+  const ExtentSet& extent_set() const { return extent_set_; }
+
+  // Returns an ordered vector of extents for |count| blocks,
+  // using extents in extent_set_. The returned extents are not
+  // removed from extent_set_. |count| must be less than or equal to
+  // the number of blocks in this extent set.
+  std::vector<Extent> GetExtentsForBlockCount(uint64_t count) const;
+
+ private:
+  ExtentSet extent_set_;
+  uint64_t blocks_;
+};
+
+// Filters out from the passed list of extents |extents| all the blocks in the
+// ExtentRanges set. Note that the order of the blocks in |extents| is preserved
+// omitting blocks present in the ExtentRanges |ranges|.
+std::vector<Extent> FilterExtentRanges(const std::vector<Extent>& extents,
+                                       const ExtentRanges& ranges);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_RANGES_H_
diff --git a/payload_generator/extent_ranges_unittest.cc b/payload_generator/extent_ranges_unittest.cc
new file mode 100644
index 0000000..8b39040
--- /dev/null
+++ b/payload_generator/extent_ranges_unittest.cc
@@ -0,0 +1,345 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/extent_ranges.h"
+
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class ExtentRangesTest : public ::testing::Test {};
+
+namespace {
+void ExpectRangeEq(const ExtentRanges& ranges,
+                   const uint64_t* expected,
+                   size_t sz,
+                   int line) {
+  uint64_t blocks = 0;
+  for (size_t i = 1; i < sz; i += 2) {
+    blocks += expected[i];
+  }
+  EXPECT_EQ(blocks, ranges.blocks()) << "line: " << line;
+
+  const ExtentRanges::ExtentSet& result = ranges.extent_set();
+  ExtentRanges::ExtentSet::const_iterator it = result.begin();
+  for (size_t i = 0; i < sz; i += 2) {
+    EXPECT_FALSE(it == result.end()) << "line: " << line;
+    EXPECT_EQ(expected[i], it->start_block()) << "line: " << line;
+    EXPECT_EQ(expected[i + 1], it->num_blocks()) << "line: " << line;
+    ++it;
+  }
+}
+
+#define EXPECT_RANGE_EQ(ranges, var)                            \
+  do {                                                          \
+    ExpectRangeEq(ranges, var, arraysize(var), __LINE__);       \
+  } while (0)
+
+void ExpectRangesOverlapOrTouch(uint64_t a_start, uint64_t a_num,
+                                uint64_t b_start, uint64_t b_num) {
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(a_start,
+                                                                 a_num),
+                                                  ExtentForRange(b_start,
+                                                                 b_num)));
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(b_start,
+                                                                 b_num),
+                                                  ExtentForRange(a_start,
+                                                                 a_num)));
+}
+
+void ExpectFalseRangesOverlapOrTouch(uint64_t a_start, uint64_t a_num,
+                                     uint64_t b_start, uint64_t b_num) {
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(a_start,
+                                                                  a_num),
+                                                   ExtentForRange(b_start,
+                                                                  b_num)));
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(b_start,
+                                                                  b_num),
+                                                   ExtentForRange(a_start,
+                                                                  a_num)));
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlap(ExtentForRange(a_start,
+                                                           a_num),
+                                            ExtentForRange(b_start,
+                                                           b_num)));
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlap(ExtentForRange(b_start,
+                                                           b_num),
+                                            ExtentForRange(a_start,
+                                                           a_num)));
+}
+
+void ExpectRangesOverlap(uint64_t a_start, uint64_t a_num,
+                         uint64_t b_start, uint64_t b_num) {
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlap(ExtentForRange(a_start,
+                                                          a_num),
+                                           ExtentForRange(b_start,
+                                                          b_num)));
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlap(ExtentForRange(b_start,
+                                                          b_num),
+                                           ExtentForRange(a_start,
+                                                          a_num)));
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(a_start,
+                                                                 a_num),
+                                                  ExtentForRange(b_start,
+                                                                 b_num)));
+  EXPECT_TRUE(ExtentRanges::ExtentsOverlapOrTouch(ExtentForRange(b_start,
+                                                                 b_num),
+                                                  ExtentForRange(a_start,
+                                                                 a_num)));
+}
+
+void ExpectFalseRangesOverlap(uint64_t a_start, uint64_t a_num,
+                              uint64_t b_start, uint64_t b_num) {
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlap(ExtentForRange(a_start,
+                                                           a_num),
+                                            ExtentForRange(b_start,
+                                                           b_num)));
+  EXPECT_FALSE(ExtentRanges::ExtentsOverlap(ExtentForRange(b_start,
+                                                           b_num),
+                                            ExtentForRange(a_start,
+                                                           a_num)));
+}
+
+}  // namespace
+
+TEST(ExtentRangesTest, ExtentsOverlapTest) {
+  ExpectRangesOverlapOrTouch(10, 20, 30, 10);
+  ExpectRangesOverlap(10, 20, 25, 10);
+  ExpectFalseRangesOverlapOrTouch(10, 20, 35, 10);
+  ExpectFalseRangesOverlap(10, 20, 30, 10);
+  ExpectRangesOverlap(12, 4, 12, 3);
+
+  ExpectRangesOverlapOrTouch(kSparseHole, 2, kSparseHole, 3);
+  ExpectRangesOverlap(kSparseHole, 2, kSparseHole, 3);
+  ExpectFalseRangesOverlapOrTouch(kSparseHole, 2, 10, 3);
+  ExpectFalseRangesOverlapOrTouch(10, 2, kSparseHole, 3);
+  ExpectFalseRangesOverlap(kSparseHole, 2, 10, 3);
+  ExpectFalseRangesOverlap(10, 2, kSparseHole, 3);
+}
+
+TEST(ExtentRangesTest, SimpleTest) {
+  ExtentRanges ranges;
+  {
+    static const uint64_t expected[] = {};
+    // Can't use arraysize() on 0-length arrays:
+    ExpectRangeEq(ranges, expected, 0, __LINE__);
+  }
+  ranges.SubtractBlock(2);
+  {
+    static const uint64_t expected[] = {};
+    // Can't use arraysize() on 0-length arrays:
+    ExpectRangeEq(ranges, expected, 0, __LINE__);
+  }
+
+  ranges.AddBlock(0);
+  ranges.Dump();
+  ranges.AddBlock(1);
+  ranges.AddBlock(3);
+
+  {
+    static const uint64_t expected[] = {0, 2, 3, 1};
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+  ranges.AddBlock(2);
+  {
+    static const uint64_t expected[] = {0, 4};
+    EXPECT_RANGE_EQ(ranges, expected);
+    ranges.AddBlock(kSparseHole);
+    EXPECT_RANGE_EQ(ranges, expected);
+    ranges.SubtractBlock(kSparseHole);
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+  ranges.SubtractBlock(2);
+  {
+    static const uint64_t expected[] = {0, 2, 3, 1};
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+
+  for (uint64_t i = 100; i < 1000; i += 100) {
+    ranges.AddExtent(ExtentForRange(i, 50));
+  }
+  {
+    static const uint64_t expected[] = {
+      0, 2, 3, 1, 100, 50, 200, 50, 300, 50, 400, 50,
+      500, 50, 600, 50, 700, 50, 800, 50, 900, 50
+    };
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+
+  ranges.SubtractExtent(ExtentForRange(210, 410 - 210));
+  {
+    static const uint64_t expected[] = {
+      0, 2, 3, 1, 100, 50, 200, 10, 410, 40, 500, 50,
+      600, 50, 700, 50, 800, 50, 900, 50
+    };
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+  ranges.AddExtent(ExtentForRange(100000, 0));
+  {
+    static const uint64_t expected[] = {
+      0, 2, 3, 1, 100, 50, 200, 10, 410, 40, 500, 50,
+      600, 50, 700, 50, 800, 50, 900, 50
+    };
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+  ranges.SubtractExtent(ExtentForRange(3, 0));
+  {
+    static const uint64_t expected[] = {
+      0, 2, 3, 1, 100, 50, 200, 10, 410, 40, 500, 50,
+      600, 50, 700, 50, 800, 50, 900, 50
+    };
+    EXPECT_RANGE_EQ(ranges, expected);
+  }
+}
+
+TEST(ExtentRangesTest, MultipleRanges) {
+  ExtentRanges ranges_a, ranges_b;
+  ranges_a.AddBlock(0);
+  ranges_b.AddBlock(4);
+  ranges_b.AddBlock(3);
+  {
+    uint64_t expected[] = {3, 2};
+    EXPECT_RANGE_EQ(ranges_b, expected);
+  }
+  ranges_a.AddRanges(ranges_b);
+  {
+    uint64_t expected[] = {0, 1, 3, 2};
+    EXPECT_RANGE_EQ(ranges_a, expected);
+  }
+  ranges_a.SubtractRanges(ranges_b);
+  {
+    uint64_t expected[] = {0, 1};
+    EXPECT_RANGE_EQ(ranges_a, expected);
+  }
+  {
+    uint64_t expected[] = {3, 2};
+    EXPECT_RANGE_EQ(ranges_b, expected);
+  }
+}
+
+TEST(ExtentRangesTest, GetExtentsForBlockCountTest) {
+  ExtentRanges ranges;
+  ranges.AddExtents(vector<Extent>(1, ExtentForRange(10, 30)));
+  {
+    vector<Extent> zero_extents = ranges.GetExtentsForBlockCount(0);
+    EXPECT_TRUE(zero_extents.empty());
+  }
+  ::google::protobuf::RepeatedPtrField<Extent> rep_field;
+  *rep_field.Add() = ExtentForRange(30, 40);
+  ranges.AddRepeatedExtents(rep_field);
+  ranges.SubtractExtents(vector<Extent>(1, ExtentForRange(20, 10)));
+  *rep_field.Mutable(0) = ExtentForRange(50, 10);
+  ranges.SubtractRepeatedExtents(rep_field);
+  EXPECT_EQ(40, ranges.blocks());
+
+  for (int i = 0; i < 2; i++) {
+    vector<Extent> expected(2);
+    expected[0] = ExtentForRange(10, 10);
+    expected[1] = ExtentForRange(30, i == 0 ? 10 : 20);
+    vector<Extent> actual =
+        ranges.GetExtentsForBlockCount(10 + expected[1].num_blocks());
+    EXPECT_EQ(expected.size(), actual.size());
+    for (vector<Extent>::size_type j = 0, e = expected.size(); j != e; ++j) {
+      EXPECT_EQ(expected[j].start_block(), actual[j].start_block())
+          << "j = " << j;
+      EXPECT_EQ(expected[j].num_blocks(), actual[j].num_blocks())
+          << "j = " << j;
+    }
+  }
+}
+
+TEST(ExtentRangesTest, ContainsBlockTest) {
+  ExtentRanges ranges;
+  EXPECT_FALSE(ranges.ContainsBlock(123));
+
+  ranges.AddExtent(ExtentForRange(10, 10));
+  ranges.AddExtent(ExtentForRange(100, 1));
+
+  EXPECT_FALSE(ranges.ContainsBlock(9));
+  EXPECT_TRUE(ranges.ContainsBlock(10));
+  EXPECT_TRUE(ranges.ContainsBlock(15));
+  EXPECT_TRUE(ranges.ContainsBlock(19));
+  EXPECT_FALSE(ranges.ContainsBlock(20));
+
+  // Test for an extent with just the block we are requesting.
+  EXPECT_FALSE(ranges.ContainsBlock(99));
+  EXPECT_TRUE(ranges.ContainsBlock(100));
+  EXPECT_FALSE(ranges.ContainsBlock(101));
+}
+
+TEST(ExtentRangesTest, FilterExtentRangesEmptyRanges) {
+  ExtentRanges ranges;
+  EXPECT_EQ(vector<Extent>(),
+            FilterExtentRanges(vector<Extent>(), ranges));
+  EXPECT_EQ(
+      vector<Extent>{ ExtentForRange(50, 10) },
+      FilterExtentRanges(vector<Extent>{ ExtentForRange(50, 10) }, ranges));
+  // Check that the empty Extents are ignored.
+  EXPECT_EQ(
+      (vector<Extent>{ ExtentForRange(10, 10), ExtentForRange(20, 10) }),
+      FilterExtentRanges(vector<Extent>{
+           ExtentForRange(10, 10),
+           ExtentForRange(3, 0),
+           ExtentForRange(20, 10) }, ranges));
+}
+
+TEST(ExtentRangesTest, FilterExtentRangesMultipleRanges) {
+  // Two overlaping extents, with three ranges to remove.
+  vector<Extent> extents {
+      ExtentForRange(10, 100),
+      ExtentForRange(30, 100) };
+  ExtentRanges ranges;
+  // This overlaps the beginning of the second extent.
+  ranges.AddExtent(ExtentForRange(28, 3));
+  ranges.AddExtent(ExtentForRange(50, 10));
+  ranges.AddExtent(ExtentForRange(70, 10));
+  // This overlaps the end of the second extent.
+  ranges.AddExtent(ExtentForRange(108, 6));
+  EXPECT_EQ(
+      (vector<Extent>{
+           // For the first extent:
+           ExtentForRange(10, 18),
+           ExtentForRange(31, 19),
+           ExtentForRange(60, 10),
+           ExtentForRange(80, 28),
+           // For the second extent:
+           ExtentForRange(31, 19),
+           ExtentForRange(60, 10),
+           ExtentForRange(80, 28),
+           ExtentForRange(114, 16)}),
+      FilterExtentRanges(extents, ranges));
+}
+
+TEST(ExtentRangesTest, FilterExtentRangesOvelapping) {
+  ExtentRanges ranges;
+  ranges.AddExtent(ExtentForRange(10, 3));
+  ranges.AddExtent(ExtentForRange(20, 5));
+  // Requested extent overlaps with one of the ranges.
+  EXPECT_EQ(vector<Extent>(),
+            FilterExtentRanges(vector<Extent>{
+                                   ExtentForRange(10, 1),
+                                   ExtentForRange(22, 1) },
+                               ranges));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/extent_utils.cc b/payload_generator/extent_utils.cc
new file mode 100644
index 0000000..1093445
--- /dev/null
+++ b/payload_generator/extent_utils.cc
@@ -0,0 +1,154 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_generator/extent_utils.h"
+
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/macros.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+void AppendBlockToExtents(vector<Extent>* extents, uint64_t block) {
+  // First try to extend the last extent in |extents|, if any.
+  if (!extents->empty()) {
+    Extent& extent = extents->back();
+    uint64_t next_block = extent.start_block() == kSparseHole ?
+        kSparseHole : extent.start_block() + extent.num_blocks();
+    if (next_block == block) {
+      extent.set_num_blocks(extent.num_blocks() + 1);
+      return;
+    }
+  }
+  // If unable to extend the last extent, append a new single-block extent.
+  Extent new_extent;
+  new_extent.set_start_block(block);
+  new_extent.set_num_blocks(1);
+  extents->push_back(new_extent);
+}
+
+Extent GetElement(const vector<Extent>& collection, size_t index) {
+  return collection[index];
+}
+
+Extent GetElement(
+    const google::protobuf::RepeatedPtrField<Extent>& collection,
+    size_t index) {
+  return collection.Get(index);
+}
+
+void ExtendExtents(
+    google::protobuf::RepeatedPtrField<Extent>* extents,
+    const google::protobuf::RepeatedPtrField<Extent>& extents_to_add) {
+  vector<Extent> extents_vector;
+  vector<Extent> extents_to_add_vector;
+  ExtentsToVector(*extents, &extents_vector);
+  ExtentsToVector(extents_to_add, &extents_to_add_vector);
+  extents_vector.insert(extents_vector.end(),
+                        extents_to_add_vector.begin(),
+                        extents_to_add_vector.end());
+  NormalizeExtents(&extents_vector);
+  extents->Clear();
+  StoreExtents(extents_vector, extents);
+}
+
+// Stores all Extents in 'extents' into 'out'.
+void StoreExtents(const vector<Extent>& extents,
+                  google::protobuf::RepeatedPtrField<Extent>* out) {
+  for (const Extent& extent : extents) {
+    Extent* new_extent = out->Add();
+    *new_extent = extent;
+  }
+}
+
+// Stores all extents in |extents| into |out_vector|.
+void ExtentsToVector(const google::protobuf::RepeatedPtrField<Extent>& extents,
+                     vector<Extent>* out_vector) {
+  out_vector->clear();
+  for (int i = 0; i < extents.size(); i++) {
+    out_vector->push_back(extents.Get(i));
+  }
+}
+
+void NormalizeExtents(vector<Extent>* extents) {
+  vector<Extent> new_extents;
+  for (const Extent& curr_ext : *extents) {
+    if (new_extents.empty()) {
+      new_extents.push_back(curr_ext);
+      continue;
+    }
+    Extent& last_ext = new_extents.back();
+    if (last_ext.start_block() + last_ext.num_blocks() ==
+        curr_ext.start_block()) {
+      // If the extents are touching, we want to combine them.
+      last_ext.set_num_blocks(last_ext.num_blocks() + curr_ext.num_blocks());
+    } else {
+      // Otherwise just include the extent as is.
+      new_extents.push_back(curr_ext);
+    }
+  }
+  *extents = new_extents;
+}
+
+vector<Extent> ExtentsSublist(const vector<Extent>& extents,
+                              uint64_t block_offset, uint64_t block_count) {
+  vector<Extent> result;
+  uint64_t scanned_blocks = 0;
+  if (block_count == 0)
+    return result;
+  uint64_t end_block_offset = block_offset + block_count;
+  for (const Extent& extent : extents) {
+    // The loop invariant is that if |extents| has enough blocks, there's
+    // still some extent to add to |result|. This implies that at the beginning
+    // of the loop scanned_blocks < block_offset + block_count.
+    if (scanned_blocks + extent.num_blocks() > block_offset) {
+      // This case implies that |extent| has some overlapping with the requested
+      // subsequence.
+      uint64_t new_start = extent.start_block();
+      uint64_t new_num_blocks = extent.num_blocks();
+      if (scanned_blocks + new_num_blocks > end_block_offset) {
+        // Cut the end part of the extent.
+        new_num_blocks = end_block_offset - scanned_blocks;
+      }
+      if (block_offset > scanned_blocks) {
+        // Cut the begin part of the extent.
+        new_num_blocks -= block_offset - scanned_blocks;
+        new_start += block_offset - scanned_blocks;
+      }
+      result.push_back(ExtentForRange(new_start, new_num_blocks));
+    }
+    scanned_blocks += extent.num_blocks();
+    if (scanned_blocks >= end_block_offset)
+      break;
+  }
+  return result;
+}
+
+bool operator==(const Extent& a, const Extent& b) {
+  return a.start_block() == b.start_block() && a.num_blocks() == b.num_blocks();
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/extent_utils.h b/payload_generator/extent_utils.h
new file mode 100644
index 0000000..91729d5
--- /dev/null
+++ b/payload_generator/extent_utils.h
@@ -0,0 +1,101 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_UTILS_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_UTILS_H_
+
+#include <vector>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/update_metadata.pb.h"
+
+// Utility functions for manipulating Extents and lists of blocks.
+
+namespace chromeos_update_engine {
+
+// |block| must either be the next block in the last extent or a block
+// in the next extent. This function will not handle inserting block
+// into an arbitrary place in the extents.
+void AppendBlockToExtents(std::vector<Extent>* extents, uint64_t block);
+
+// Get/SetElement are intentionally overloaded so that templated functions
+// can accept either type of collection of Extents.
+Extent GetElement(const std::vector<Extent>& collection, size_t index);
+Extent GetElement(
+    const google::protobuf::RepeatedPtrField<Extent>& collection,
+    size_t index);
+
+// Return the total number of blocks in a collection (vector or
+// RepeatedPtrField) of Extents.
+template<typename T>
+uint64_t BlocksInExtents(const T& collection) {
+  uint64_t ret = 0;
+  for (size_t i = 0; i < static_cast<size_t>(collection.size()); ++i) {
+    ret += GetElement(collection, i).num_blocks();
+  }
+  return ret;
+}
+
+// Takes a collection (vector or RepeatedPtrField) of Extent and
+// returns a vector of the blocks referenced, in order.
+template<typename T>
+std::vector<uint64_t> ExpandExtents(const T& extents) {
+  std::vector<uint64_t> ret;
+  for (size_t i = 0, e = static_cast<size_t>(extents.size()); i != e; ++i) {
+    const Extent extent = GetElement(extents, i);
+    if (extent.start_block() == kSparseHole) {
+      ret.resize(ret.size() + extent.num_blocks(), kSparseHole);
+    } else {
+      for (uint64_t block = extent.start_block();
+           block < (extent.start_block() + extent.num_blocks()); block++) {
+        ret.push_back(block);
+      }
+    }
+  }
+  return ret;
+}
+
+// Stores all Extents in 'extents' into 'out'.
+void StoreExtents(const std::vector<Extent>& extents,
+                  google::protobuf::RepeatedPtrField<Extent>* out);
+
+// Stores all extents in |extents| into |out_vector|.
+void ExtentsToVector(const google::protobuf::RepeatedPtrField<Extent>& extents,
+                     std::vector<Extent>* out_vector);
+
+// Takes a pointer to extents |extents| and extents |extents_to_add|, and
+// merges them by adding |extents_to_add| to |extents| and normalizing.
+void ExtendExtents(
+  google::protobuf::RepeatedPtrField<Extent>* extents,
+  const google::protobuf::RepeatedPtrField<Extent>& extents_to_add);
+
+// Takes a vector of extents and normalizes those extents. Expects the extents
+// to be sorted by start block. E.g. if |extents| is [(1, 2), (3, 5), (10, 2)]
+// then |extents| will be changed to [(1, 7), (10, 2)].
+void NormalizeExtents(std::vector<Extent>* extents);
+
+// Return a subsequence of the list of blocks passed. Both the passed list of
+// blocks |extents| and the return value are expressed as a list of Extent, not
+// blocks. The returned list skips the first |block_offset| blocks from the
+// |extents| and cotains |block_count| blocks (or less if |extents| is shorter).
+std::vector<Extent> ExtentsSublist(const std::vector<Extent>& extents,
+                                   uint64_t block_offset, uint64_t block_count);
+
+bool operator==(const Extent& a, const Extent& b);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_EXTENT_UTILS_H_
diff --git a/payload_generator/extent_utils_unittest.cc b/payload_generator/extent_utils_unittest.cc
new file mode 100644
index 0000000..62c8ff1
--- /dev/null
+++ b/payload_generator/extent_utils_unittest.cc
@@ -0,0 +1,164 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/extent_utils.h"
+
+#include <utility>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class ExtentUtilsTest : public ::testing::Test {};
+
+TEST(ExtentUtilsTest, AppendSparseToExtentsTest) {
+  vector<Extent> extents;
+
+  EXPECT_EQ(0, extents.size());
+  AppendBlockToExtents(&extents, kSparseHole);
+  EXPECT_EQ(1, extents.size());
+  AppendBlockToExtents(&extents, 0);
+  EXPECT_EQ(2, extents.size());
+  AppendBlockToExtents(&extents, kSparseHole);
+  AppendBlockToExtents(&extents, kSparseHole);
+
+  ASSERT_EQ(3, extents.size());
+  EXPECT_EQ(kSparseHole, extents[0].start_block());
+  EXPECT_EQ(1, extents[0].num_blocks());
+  EXPECT_EQ(0, extents[1].start_block());
+  EXPECT_EQ(1, extents[1].num_blocks());
+  EXPECT_EQ(kSparseHole, extents[2].start_block());
+  EXPECT_EQ(2, extents[2].num_blocks());
+}
+
+TEST(ExtentUtilsTest, BlocksInExtentsTest) {
+  {
+    vector<Extent> extents;
+    EXPECT_EQ(0, BlocksInExtents(extents));
+    extents.push_back(ExtentForRange(0, 1));
+    EXPECT_EQ(1, BlocksInExtents(extents));
+    extents.push_back(ExtentForRange(23, 55));
+    EXPECT_EQ(56, BlocksInExtents(extents));
+    extents.push_back(ExtentForRange(1, 2));
+    EXPECT_EQ(58, BlocksInExtents(extents));
+  }
+  {
+    google::protobuf::RepeatedPtrField<Extent> extents;
+    EXPECT_EQ(0, BlocksInExtents(extents));
+    *extents.Add() = ExtentForRange(0, 1);
+    EXPECT_EQ(1, BlocksInExtents(extents));
+    *extents.Add() = ExtentForRange(23, 55);
+    EXPECT_EQ(56, BlocksInExtents(extents));
+    *extents.Add() = ExtentForRange(1, 2);
+    EXPECT_EQ(58, BlocksInExtents(extents));
+  }
+}
+
+TEST(ExtentUtilsTest, ExtendExtentsTest) {
+  InstallOperation first_op;
+  *(first_op.add_src_extents()) = ExtentForRange(1, 1);
+  *(first_op.add_src_extents()) = ExtentForRange(3, 1);
+
+  InstallOperation second_op;
+  *(second_op.add_src_extents()) = ExtentForRange(4, 2);
+  *(second_op.add_src_extents()) = ExtentForRange(8, 2);
+
+  ExtendExtents(first_op.mutable_src_extents(), second_op.src_extents());
+  vector<Extent> first_op_vec;
+  ExtentsToVector(first_op.src_extents(), &first_op_vec);
+  EXPECT_EQ((vector<Extent>{
+      ExtentForRange(1, 1),
+      ExtentForRange(3, 3),
+      ExtentForRange(8, 2)}), first_op_vec);
+}
+
+TEST(ExtentUtilsTest, NormalizeExtentsSimpleList) {
+  // Make sure it works when there's just one extent.
+  vector<Extent> extents;
+  NormalizeExtents(&extents);
+  EXPECT_EQ(0, extents.size());
+
+  extents = { ExtentForRange(0, 3) };
+  NormalizeExtents(&extents);
+  EXPECT_EQ(1, extents.size());
+  EXPECT_EQ(ExtentForRange(0, 3), extents[0]);
+}
+
+TEST(ExtentUtilsTest, NormalizeExtentsTest) {
+  vector<Extent> extents = {
+      ExtentForRange(0, 3),
+      ExtentForRange(3, 2),
+      ExtentForRange(5, 1),
+      ExtentForRange(8, 4),
+      ExtentForRange(13, 1),
+      ExtentForRange(14, 2)
+  };
+  NormalizeExtents(&extents);
+  EXPECT_EQ(3, extents.size());
+  EXPECT_EQ(ExtentForRange(0, 6), extents[0]);
+  EXPECT_EQ(ExtentForRange(8, 4), extents[1]);
+  EXPECT_EQ(ExtentForRange(13, 3), extents[2]);
+}
+
+TEST(ExtentUtilsTest, ExtentsSublistTest) {
+  vector<Extent> extents = {
+      ExtentForRange(10, 10),
+      ExtentForRange(30, 10),
+      ExtentForRange(50, 10)
+  };
+
+  // Simple empty result cases.
+  EXPECT_EQ(vector<Extent>(),
+            ExtentsSublist(extents, 1000, 20));
+  EXPECT_EQ(vector<Extent>(),
+            ExtentsSublist(extents, 5, 0));
+  EXPECT_EQ(vector<Extent>(),
+            ExtentsSublist(extents, 30, 1));
+
+  // Normal test cases.
+  EXPECT_EQ(vector<Extent>{ ExtentForRange(13, 2) },
+            ExtentsSublist(extents, 3, 2));
+  EXPECT_EQ(vector<Extent>{ ExtentForRange(15, 5) },
+            ExtentsSublist(extents, 5, 5));
+  EXPECT_EQ((vector<Extent>{ ExtentForRange(15, 5), ExtentForRange(30, 5) }),
+            ExtentsSublist(extents, 5, 10));
+  EXPECT_EQ((vector<Extent>{
+                 ExtentForRange(13, 7),
+                 ExtentForRange(30, 10),
+                 ExtentForRange(50, 3), }),
+            ExtentsSublist(extents, 3, 20));
+
+  // Extact match case.
+  EXPECT_EQ(vector<Extent>{ ExtentForRange(30, 10) },
+            ExtentsSublist(extents, 10, 10));
+  EXPECT_EQ(vector<Extent>{ ExtentForRange(50, 10) },
+            ExtentsSublist(extents, 20, 10));
+
+  // Cases where the requested num_blocks is too big.
+  EXPECT_EQ(vector<Extent>{ ExtentForRange(53, 7) },
+            ExtentsSublist(extents, 23, 100));
+  EXPECT_EQ((vector<Extent>{ ExtentForRange(34, 6), ExtentForRange(50, 10) }),
+            ExtentsSublist(extents, 14, 100));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/fake_filesystem.cc b/payload_generator/fake_filesystem.cc
new file mode 100644
index 0000000..3a6458d
--- /dev/null
+++ b/payload_generator/fake_filesystem.cc
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/fake_filesystem.h"
+
+#include <gtest/gtest.h>
+
+namespace chromeos_update_engine {
+
+FakeFilesystem::FakeFilesystem(uint64_t block_size, uint64_t block_count) :
+    block_size_(block_size),
+    block_count_(block_count) {
+}
+
+size_t FakeFilesystem::GetBlockSize() const {
+  return block_size_;
+}
+
+size_t FakeFilesystem::GetBlockCount() const {
+  return block_count_;
+}
+
+bool FakeFilesystem::GetFiles(std::vector<File>* files) const {
+  *files = files_;
+  return true;
+}
+
+void FakeFilesystem::AddFile(const std::string& filename,
+                             const std::vector<Extent> extents) {
+  File file;
+  file.name = filename;
+  file.extents = extents;
+  for (const Extent& extent : extents) {
+    EXPECT_LE(0, extent.start_block());
+    EXPECT_LE(extent.start_block() + extent.num_blocks(), block_count_);
+  }
+  files_.push_back(file);
+}
+
+bool FakeFilesystem::LoadSettings(brillo::KeyValueStore* store) const {
+  if (minor_version_ < 0)
+    return false;
+  store->SetString("PAYLOAD_MINOR_VERSION", std::to_string(minor_version_));
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/fake_filesystem.h b/payload_generator/fake_filesystem.h
new file mode 100644
index 0000000..a14b8d3
--- /dev/null
+++ b/payload_generator/fake_filesystem.h
@@ -0,0 +1,68 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_FAKE_FILESYSTEM_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_FAKE_FILESYSTEM_H_
+
+// A fake filesystem interface implementation allowing the user to add arbitrary
+// files/metadata.
+
+#include "update_engine/payload_generator/filesystem_interface.h"
+
+#include <string>
+#include <vector>
+
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+class FakeFilesystem : public FilesystemInterface {
+ public:
+  FakeFilesystem(uint64_t block_size, uint64_t block_count);
+  virtual ~FakeFilesystem() = default;
+
+  // FilesystemInterface overrides.
+  size_t GetBlockSize() const override;
+  size_t GetBlockCount() const override;
+  bool GetFiles(std::vector<File>* files) const override;
+  bool LoadSettings(brillo::KeyValueStore* store) const override;
+
+  // Fake methods.
+
+  // Add a file to the list of fake files.
+  void AddFile(const std::string& filename, const std::vector<Extent> extents);
+
+  // Sets the PAYLOAD_MINOR_VERSION key stored by LoadSettings(). Use a negative
+  // value to produce an error in LoadSettings().
+  void SetMinorVersion(int minor_version) {
+    minor_version_ = minor_version;
+  }
+
+ private:
+  FakeFilesystem() = default;
+
+  uint64_t block_size_;
+  uint64_t block_count_;
+  int minor_version_{-1};
+
+  std::vector<File> files_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeFilesystem);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_FAKE_FILESYSTEM_H_
diff --git a/payload_generator/filesystem_interface.h b/payload_generator/filesystem_interface.h
new file mode 100644
index 0000000..866c46b
--- /dev/null
+++ b/payload_generator/filesystem_interface.h
@@ -0,0 +1,95 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_FILESYSTEM_INTERFACE_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_FILESYSTEM_INTERFACE_H_
+
+// This class is used to abstract a filesystem and iterate the blocks
+// associated with the files and filesystem structures.
+// For the purposes of the update payload generation, a filesystem is a formated
+// partition composed by fixed-size blocks, since that's the interface used in
+// the update payload.
+
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/key_value_store.h>
+
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+class FilesystemInterface {
+ public:
+  // This represents a file or pseudo-file in the filesystem. It can include
+  // all sort of files, like symlinks, hardlinks, directories and even a file
+  // entry representing the metadata, free space, journaling data, etc.
+  struct File {
+    File() {
+      memset(&file_stat, 0, sizeof(file_stat));
+    }
+
+    // The stat struct for the file. This is invalid (inode 0) for some
+    // pseudo-files.
+    struct stat file_stat;
+
+    // The absolute path to the file inside the filesystem, for example,
+    // "/usr/bin/bash". For pseudo-files, like blocks associated to internal
+    // filesystem tables or free space, the path doesn't start with a /.
+    std::string name;
+
+    // The list of all physical blocks holding the data of this file in
+    // the same order as the logical data. All the block numbers shall be
+    // between 0 and GetBlockCount() - 1. The blocks are encoded in extents,
+    // indicating the starting block, and the number of consecutive blocks.
+    std::vector<Extent> extents;
+  };
+
+  virtual ~FilesystemInterface() = default;
+
+  // Returns the size of a block in the filesystem.
+  virtual size_t GetBlockSize() const = 0;
+
+  // Returns the number of blocks in the filesystem.
+  virtual size_t GetBlockCount() const = 0;
+
+  // Stores in |files| the list of files and pseudo-files in the filesystem. See
+  // FileInterface for details. The paths returned by this method shall not
+  // be repeated; but the same block could be present in more than one file as
+  // happens for example with hard-linked files, but not limited to those cases.
+  // Returns whether the function succeeded.
+  virtual bool GetFiles(std::vector<File>* files) const = 0;
+
+  // Load the image settings stored in the filesystem in the
+  // /etc/update_engine.conf file. Returns whether the settings were found.
+  virtual bool LoadSettings(brillo::KeyValueStore* store) const = 0;
+
+ protected:
+  FilesystemInterface() = default;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(FilesystemInterface);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_FILESYSTEM_INTERFACE_H_
diff --git a/payload_generator/full_update_generator.cc b/payload_generator/full_update_generator.cc
new file mode 100644
index 0000000..56a3ca8
--- /dev/null
+++ b/payload_generator/full_update_generator.cc
@@ -0,0 +1,203 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_generator/full_update_generator.h"
+
+#include <fcntl.h>
+#include <inttypes.h>
+
+#include <algorithm>
+#include <deque>
+#include <memory>
+
+#include <base/format_macros.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <base/synchronization/lock.h>
+#include <base/threading/simple_thread.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/bzip.h"
+
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+const size_t kDefaultFullChunkSize = 1024 * 1024;  // 1 MiB
+
+// This class encapsulates a full update chunk processing thread work. The
+// processor reads a chunk of data from the input file descriptor and compresses
+// it. The processor will destroy itself when the work is done.
+class ChunkProcessor : public base::DelegateSimpleThread::Delegate {
+ public:
+  // Read a chunk of |size| bytes from |fd| starting at offset |offset|.
+  ChunkProcessor(int fd, off_t offset, size_t size,
+                 BlobFileWriter* blob_file, AnnotatedOperation* aop)
+    : fd_(fd),
+      offset_(offset),
+      size_(size),
+      blob_file_(blob_file),
+      aop_(aop) {}
+  // We use a default move constructor since all the data members are POD types.
+  ChunkProcessor(ChunkProcessor&&) = default;
+  ~ChunkProcessor() override = default;
+
+  // Overrides DelegateSimpleThread::Delegate.
+  // Run() handles the read from |fd| in a thread-safe way, and stores the
+  // new operation to generate the region starting at |offset| of size |size|
+  // in the output operation |aop|. The associated blob data is stored in
+  // |blob_fd| and |blob_file_size| is updated.
+  void Run() override;
+
+ private:
+  bool ProcessChunk();
+
+  // Work parameters.
+  int fd_;
+  off_t offset_;
+  size_t size_;
+  BlobFileWriter* blob_file_;
+  AnnotatedOperation* aop_;
+
+  DISALLOW_COPY_AND_ASSIGN(ChunkProcessor);
+};
+
+void ChunkProcessor::Run() {
+  if (!ProcessChunk()) {
+    LOG(ERROR) << "Error processing region at " << offset_ << " of size "
+               << size_;
+  }
+}
+
+bool ChunkProcessor::ProcessChunk() {
+  brillo::Blob buffer_in_(size_);
+  brillo::Blob op_blob;
+  ssize_t bytes_read = -1;
+  TEST_AND_RETURN_FALSE(utils::PReadAll(fd_,
+                                        buffer_in_.data(),
+                                        buffer_in_.size(),
+                                        offset_,
+                                        &bytes_read));
+  TEST_AND_RETURN_FALSE(bytes_read == static_cast<ssize_t>(size_));
+  TEST_AND_RETURN_FALSE(BzipCompress(buffer_in_, &op_blob));
+
+  InstallOperation_Type op_type = InstallOperation::REPLACE_BZ;
+
+  if (op_blob.size() >= buffer_in_.size()) {
+    // A REPLACE is cheaper than a REPLACE_BZ in this case.
+    op_blob = std::move(buffer_in_);
+    op_type = InstallOperation::REPLACE;
+  }
+
+  TEST_AND_RETURN_FALSE(aop_->SetOperationBlob(&op_blob, blob_file_));
+  aop_->op.set_type(op_type);
+  return true;
+}
+
+}  // namespace
+
+bool FullUpdateGenerator::GenerateOperations(
+    const PayloadGenerationConfig& config,
+    const PartitionConfig& old_part,
+    const PartitionConfig& new_part,
+    BlobFileWriter* blob_file,
+    vector<AnnotatedOperation>* aops) {
+  TEST_AND_RETURN_FALSE(new_part.ValidateExists());
+
+  // FullUpdateGenerator requires a positive chunk_size, otherwise there will
+  // be only one operation with the whole partition which should not be allowed.
+  // For performance reasons, we force a small default hard limit of 1 MiB. This
+  // limit can be changed in the config, and we will use the smaller of the two
+  // soft/hard limits.
+  size_t full_chunk_size;
+  if (config.hard_chunk_size >= 0) {
+    full_chunk_size = std::min(static_cast<size_t>(config.hard_chunk_size),
+                               config.soft_chunk_size);
+  } else {
+    full_chunk_size = std::min(kDefaultFullChunkSize, config.soft_chunk_size);
+    LOG(INFO) << "No chunk_size provided, using the default chunk_size for the "
+              << "full operations: " << full_chunk_size << " bytes.";
+  }
+  TEST_AND_RETURN_FALSE(full_chunk_size > 0);
+  TEST_AND_RETURN_FALSE(full_chunk_size % config.block_size == 0);
+
+  size_t chunk_blocks = full_chunk_size / config.block_size;
+  size_t max_threads = std::max(sysconf(_SC_NPROCESSORS_ONLN), 4L);
+  LOG(INFO) << "Compressing partition " << new_part.name
+            << " from " << new_part.path << " splitting in chunks of "
+            << chunk_blocks << " blocks (" << config.block_size
+            << " bytes each) using " << max_threads << " threads";
+
+  int in_fd = open(new_part.path.c_str(), O_RDONLY, 0);
+  TEST_AND_RETURN_FALSE(in_fd >= 0);
+  ScopedFdCloser in_fd_closer(&in_fd);
+
+  // We potentially have all the ChunkProcessors in memory but only
+  // |max_threads| will actually hold a block in memory while we process.
+  size_t partition_blocks = new_part.size / config.block_size;
+  size_t num_chunks = (partition_blocks + chunk_blocks - 1) / chunk_blocks;
+  aops->resize(num_chunks);
+  vector<ChunkProcessor> chunk_processors;
+  chunk_processors.reserve(num_chunks);
+  blob_file->SetTotalBlobs(num_chunks);
+
+  for (size_t i = 0; i < num_chunks; ++i) {
+    size_t start_block = i * chunk_blocks;
+    // The last chunk could be smaller.
+    size_t num_blocks = std::min(chunk_blocks,
+                                 partition_blocks - i * chunk_blocks);
+
+    // Preset all the static information about the operations. The
+    // ChunkProcessor will set the rest.
+    AnnotatedOperation* aop = aops->data() + i;
+    aop->name = base::StringPrintf("<%s-operation-%" PRIuS ">",
+                                   new_part.name.c_str(), i);
+    Extent* dst_extent = aop->op.add_dst_extents();
+    dst_extent->set_start_block(start_block);
+    dst_extent->set_num_blocks(num_blocks);
+
+    chunk_processors.emplace_back(
+        in_fd,
+        static_cast<off_t>(start_block) * config.block_size,
+        num_blocks * config.block_size,
+        blob_file,
+        aop);
+  }
+
+  // Thread pool used for worker threads.
+  base::DelegateSimpleThreadPool thread_pool("full-update-generator",
+                                             max_threads);
+  thread_pool.Start();
+  for (ChunkProcessor& processor : chunk_processors)
+    thread_pool.AddWork(&processor);
+  thread_pool.JoinAll();
+
+  // All the work done, disable logging.
+  blob_file->SetTotalBlobs(0);
+
+  // All the operations must have a type set at this point. Otherwise, a
+  // ChunkProcessor failed to complete.
+  for (const AnnotatedOperation& aop : *aops) {
+    if (!aop.op.has_type())
+      return false;
+  }
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/full_update_generator.h b/payload_generator/full_update_generator.h
new file mode 100644
index 0000000..d722028
--- /dev/null
+++ b/payload_generator/full_update_generator.h
@@ -0,0 +1,53 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_FULL_UPDATE_GENERATOR_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_FULL_UPDATE_GENERATOR_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/payload_generator/operations_generator.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+
+namespace chromeos_update_engine {
+
+class FullUpdateGenerator : public OperationsGenerator {
+ public:
+  FullUpdateGenerator() = default;
+
+  // OperationsGenerator override.
+  // Creates a full update for the target image defined in |config|. |config|
+  // must be a valid payload generation configuration for a full payload.
+  // Populates |aops|, with data about the update operations, and writes
+  // relevant data to |blob_file|.
+  bool GenerateOperations(
+      const PayloadGenerationConfig& config,
+      const PartitionConfig& old_part,
+      const PartitionConfig& new_part,
+      BlobFileWriter* blob_file,
+      std::vector<AnnotatedOperation>* aops) override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(FullUpdateGenerator);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_FULL_UPDATE_GENERATOR_H_
diff --git a/payload_generator/full_update_generator_unittest.cc b/payload_generator/full_update_generator_unittest.cc
new file mode 100644
index 0000000..d46346d
--- /dev/null
+++ b/payload_generator/full_update_generator_unittest.cc
@@ -0,0 +1,142 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/full_update_generator.h"
+
+#include <string>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using chromeos_update_engine::test_utils::FillWithData;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class FullUpdateGeneratorTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    config_.is_delta = false;
+    config_.minor_version = kFullPayloadMinorVersion;
+    config_.hard_chunk_size = 128 * 1024;
+    config_.block_size = 4096;
+
+    EXPECT_TRUE(utils::MakeTempFile("FullUpdateTest_partition.XXXXXX",
+                                    &new_part_conf.path,
+                                    nullptr));
+    EXPECT_TRUE(utils::MakeTempFile("FullUpdateTest_blobs.XXXXXX",
+                                    &out_blobs_path_,
+                                    &out_blobs_fd_));
+
+    blob_file_.reset(new BlobFileWriter(out_blobs_fd_, &out_blobs_length_));
+    part_path_unlinker_.reset(new ScopedPathUnlinker(new_part_conf.path));
+    out_blobs_unlinker_.reset(new ScopedPathUnlinker(out_blobs_path_));
+  }
+
+  PayloadGenerationConfig config_;
+  PartitionConfig new_part_conf{"part"};
+
+  vector<AnnotatedOperation> aops;
+
+  // Output file holding the payload blobs.
+  string out_blobs_path_;
+  int out_blobs_fd_{-1};
+  off_t out_blobs_length_{0};
+  ScopedFdCloser out_blobs_fd_closer_{&out_blobs_fd_};
+
+  std::unique_ptr<BlobFileWriter> blob_file_;
+  std::unique_ptr<ScopedPathUnlinker> part_path_unlinker_;
+  std::unique_ptr<ScopedPathUnlinker> out_blobs_unlinker_;
+
+  // FullUpdateGenerator under test.
+  FullUpdateGenerator generator_;
+};
+
+TEST_F(FullUpdateGeneratorTest, RunTest) {
+  brillo::Blob new_part(9 * 1024 * 1024);
+  FillWithData(&new_part);
+  new_part_conf.size = new_part.size();
+
+  EXPECT_TRUE(test_utils::WriteFileVector(new_part_conf.path, new_part));
+
+  EXPECT_TRUE(generator_.GenerateOperations(config_,
+                                            new_part_conf,  // this is ignored
+                                            new_part_conf,
+                                            blob_file_.get(),
+                                            &aops));
+  int64_t new_part_chunks = new_part_conf.size / config_.hard_chunk_size;
+  EXPECT_EQ(new_part_chunks, aops.size());
+  for (off_t i = 0; i < new_part_chunks; ++i) {
+    EXPECT_EQ(1, aops[i].op.dst_extents_size());
+    EXPECT_EQ(i * config_.hard_chunk_size / config_.block_size,
+              aops[i].op.dst_extents(0).start_block()) << "i = " << i;
+    EXPECT_EQ(config_.hard_chunk_size / config_.block_size,
+              aops[i].op.dst_extents(0).num_blocks());
+    if (aops[i].op.type() != InstallOperation::REPLACE) {
+      EXPECT_EQ(InstallOperation::REPLACE_BZ, aops[i].op.type());
+    }
+  }
+}
+
+// Test that if the chunk size is not a divisor of the image size, it handles
+// correctly the last chunk of the partition.
+TEST_F(FullUpdateGeneratorTest, ChunkSizeTooBig) {
+  config_.hard_chunk_size = 1024 * 1024;
+  config_.soft_chunk_size = config_.hard_chunk_size;
+  brillo::Blob new_part(1536 * 1024);  // 1.5 MiB
+  new_part_conf.size = new_part.size();
+
+  EXPECT_TRUE(test_utils::WriteFileVector(new_part_conf.path, new_part));
+
+  EXPECT_TRUE(generator_.GenerateOperations(config_,
+                                            new_part_conf,  // this is ignored
+                                            new_part_conf,
+                                            blob_file_.get(),
+                                            &aops));
+  // new_part has one chunk and a half.
+  EXPECT_EQ(2, aops.size());
+  EXPECT_EQ(config_.hard_chunk_size / config_.block_size,
+            BlocksInExtents(aops[0].op.dst_extents()));
+  EXPECT_EQ((new_part.size() - config_.hard_chunk_size) / config_.block_size,
+            BlocksInExtents(aops[1].op.dst_extents()));
+}
+
+// Test that if the image size is much smaller than the chunk size, it handles
+// correctly the only chunk of the partition.
+TEST_F(FullUpdateGeneratorTest, ImageSizeTooSmall) {
+  brillo::Blob new_part(16 * 1024);
+  new_part_conf.size = new_part.size();
+
+  EXPECT_TRUE(test_utils::WriteFileVector(new_part_conf.path, new_part));
+
+  EXPECT_TRUE(generator_.GenerateOperations(config_,
+                                            new_part_conf,  // this is ignored
+                                            new_part_conf,
+                                            blob_file_.get(),
+                                            &aops));
+
+  // new_part has less than one chunk.
+  EXPECT_EQ(1, aops.size());
+  EXPECT_EQ(new_part.size() / config_.block_size,
+            BlocksInExtents(aops[0].op.dst_extents()));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/generate_delta_main.cc b/payload_generator/generate_delta_main.cc
new file mode 100644
index 0000000..f462347
--- /dev/null
+++ b/payload_generator/generate_delta_main.cc
@@ -0,0 +1,546 @@
+//
+// Copyright (C) 2010 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 <errno.h>
+#include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <set>
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <base/strings/string_split.h>
+#include <brillo/flag_helper.h>
+#include <brillo/key_value_store.h>
+
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/terminator.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/delta_diff_utils.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+#include "update_engine/payload_generator/payload_signer.h"
+#include "update_engine/update_metadata.pb.h"
+
+// This file contains a simple program that takes an old path, a new path,
+// and an output file as arguments and the path to an output file and
+// generates a delta that can be sent to Chrome OS clients.
+
+using std::set;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+void ParseSignatureSizes(const string& signature_sizes_flag,
+                         vector<int>* signature_sizes) {
+  signature_sizes->clear();
+  vector<string> split_strings;
+
+  base::SplitString(signature_sizes_flag, ':', &split_strings);
+  for (const string& str : split_strings) {
+    int size = 0;
+    bool parsing_successful = base::StringToInt(str, &size);
+    LOG_IF(FATAL, !parsing_successful)
+        << "Invalid signature size: " << str;
+
+    LOG_IF(FATAL, size != (2048 / 8)) <<
+        "Only signature sizes of 256 bytes are supported.";
+
+    signature_sizes->push_back(size);
+  }
+}
+
+bool ParseImageInfo(const string& channel,
+                    const string& board,
+                    const string& version,
+                    const string& key,
+                    const string& build_channel,
+                    const string& build_version,
+                    ImageInfo* image_info) {
+  // All of these arguments should be present or missing.
+  bool empty = channel.empty();
+
+  CHECK_EQ(channel.empty(), empty);
+  CHECK_EQ(board.empty(), empty);
+  CHECK_EQ(version.empty(), empty);
+  CHECK_EQ(key.empty(), empty);
+
+  if (empty)
+    return false;
+
+  image_info->set_channel(channel);
+  image_info->set_board(board);
+  image_info->set_version(version);
+  image_info->set_key(key);
+
+  image_info->set_build_channel(
+      build_channel.empty() ? channel : build_channel);
+
+  image_info->set_build_version(
+      build_version.empty() ? version : build_version);
+
+  return true;
+}
+
+void CalculateHashForSigning(const vector<int> &sizes,
+                             const string& out_hash_file,
+                             const string& out_metadata_hash_file,
+                             const string& in_file) {
+  LOG(INFO) << "Calculating hash for signing.";
+  LOG_IF(FATAL, in_file.empty())
+      << "Must pass --in_file to calculate hash for signing.";
+  LOG_IF(FATAL, out_hash_file.empty())
+      << "Must pass --out_hash_file to calculate hash for signing.";
+
+  brillo::Blob payload_hash, metadata_hash;
+  CHECK(PayloadSigner::HashPayloadForSigning(in_file, sizes, &payload_hash,
+                                             &metadata_hash));
+  CHECK(utils::WriteFile(out_hash_file.c_str(), payload_hash.data(),
+                         payload_hash.size()));
+  if (!out_metadata_hash_file.empty())
+    CHECK(utils::WriteFile(out_metadata_hash_file.c_str(), metadata_hash.data(),
+                           metadata_hash.size()));
+
+  LOG(INFO) << "Done calculating hash for signing.";
+}
+
+void SignatureFileFlagToBlobs(const string& signature_file_flag,
+                              vector<brillo::Blob>* signatures) {
+  vector<string> signature_files;
+  base::SplitString(signature_file_flag, ':', &signature_files);
+  for (const string& signature_file : signature_files) {
+    brillo::Blob signature;
+    CHECK(utils::ReadFile(signature_file, &signature));
+    signatures->push_back(signature);
+  }
+}
+
+void SignPayload(const string& in_file,
+                 const string& out_file,
+                 const string& payload_signature_file,
+                 const string& metadata_signature_file,
+                 const string& out_metadata_size_file) {
+  LOG(INFO) << "Signing payload.";
+  LOG_IF(FATAL, in_file.empty())
+      << "Must pass --in_file to sign payload.";
+  LOG_IF(FATAL, out_file.empty())
+      << "Must pass --out_file to sign payload.";
+  LOG_IF(FATAL, payload_signature_file.empty())
+      << "Must pass --signature_file to sign payload.";
+  vector<brillo::Blob> signatures, metadata_signatures;
+  SignatureFileFlagToBlobs(payload_signature_file, &signatures);
+  SignatureFileFlagToBlobs(metadata_signature_file, &metadata_signatures);
+  uint64_t final_metadata_size;
+  CHECK(PayloadSigner::AddSignatureToPayload(in_file, signatures,
+      metadata_signatures, out_file, &final_metadata_size));
+  LOG(INFO) << "Done signing payload. Final metadata size = "
+            << final_metadata_size;
+  if (!out_metadata_size_file.empty()) {
+    string metadata_size_string = std::to_string(final_metadata_size);
+    CHECK(utils::WriteFile(out_metadata_size_file.c_str(),
+                           metadata_size_string.data(),
+                           metadata_size_string.size()));
+  }
+}
+
+void VerifySignedPayload(const string& in_file,
+                         const string& public_key) {
+  LOG(INFO) << "Verifying signed payload.";
+  LOG_IF(FATAL, in_file.empty())
+      << "Must pass --in_file to verify signed payload.";
+  LOG_IF(FATAL, public_key.empty())
+      << "Must pass --public_key to verify signed payload.";
+  CHECK(PayloadSigner::VerifySignedPayload(in_file, public_key));
+  LOG(INFO) << "Done verifying signed payload.";
+}
+
+// TODO(deymo): This function is likely broken for deltas minor version 2 or
+// newer. Move this function to a new file and make the delta_performer
+// integration tests use this instead.
+void ApplyDelta(const string& in_file,
+                const string& old_kernel,
+                const string& old_rootfs,
+                const string& prefs_dir) {
+  LOG(INFO) << "Applying delta.";
+  LOG_IF(FATAL, old_rootfs.empty())
+      << "Must pass --old_image to apply delta.";
+  Prefs prefs;
+  InstallPlan install_plan;
+  LOG(INFO) << "Setting up preferences under: " << prefs_dir;
+  LOG_IF(ERROR, !prefs.Init(base::FilePath(prefs_dir)))
+      << "Failed to initialize preferences.";
+  // Get original checksums
+  LOG(INFO) << "Calculating original checksums";
+  ImageConfig old_image;
+  old_image.partitions.emplace_back(kLegacyPartitionNameRoot);
+  old_image.partitions.back().path = old_rootfs;
+  old_image.partitions.emplace_back(kLegacyPartitionNameKernel);
+  old_image.partitions.back().path = old_kernel;
+  CHECK(old_image.LoadImageSize());
+  for (const auto& old_part : old_image.partitions) {
+    PartitionInfo part_info;
+    CHECK(diff_utils::InitializePartitionInfo(old_part, &part_info));
+    InstallPlan::Partition part;
+    part.name = old_part.name;
+    part.source_hash.assign(part_info.hash().begin(),
+                            part_info.hash().end());
+    part.source_path = old_part.path;
+    // Apply the delta in-place to the old_part.
+    part.target_path = old_part.path;
+    install_plan.partitions.push_back(part);
+  }
+
+  DeltaPerformer performer(&prefs, nullptr, nullptr, nullptr, &install_plan);
+  brillo::Blob buf(1024 * 1024);
+  int fd = open(in_file.c_str(), O_RDONLY, 0);
+  CHECK_GE(fd, 0);
+  ScopedFdCloser fd_closer(&fd);
+  for (off_t offset = 0;; offset += buf.size()) {
+    ssize_t bytes_read;
+    CHECK(utils::PReadAll(fd, buf.data(), buf.size(), offset, &bytes_read));
+    if (bytes_read == 0)
+      break;
+    CHECK_EQ(performer.Write(buf.data(), bytes_read), bytes_read);
+  }
+  CHECK_EQ(performer.Close(), 0);
+  DeltaPerformer::ResetUpdateProgress(&prefs, false);
+  LOG(INFO) << "Done applying delta.";
+}
+
+int Main(int argc, char** argv) {
+  DEFINE_string(old_image, "", "Path to the old rootfs");
+  DEFINE_string(new_image, "", "Path to the new rootfs");
+  DEFINE_string(old_kernel, "", "Path to the old kernel partition image");
+  DEFINE_string(new_kernel, "", "Path to the new kernel partition image");
+  DEFINE_string(old_partitions, "",
+                "Path to the old partitions. To pass multiple partitions, use "
+                "a single argument with a colon between paths, e.g. "
+                "/path/to/part:/path/to/part2::/path/to/last_part . Path can "
+                "be empty, but it has to match the order of partition_names.");
+  DEFINE_string(new_partitions, "",
+                "Path to the new partitions. To pass multiple partitions, use "
+                "a single argument with a colon between paths, e.g. "
+                "/path/to/part:/path/to/part2:/path/to/last_part . Path has "
+                "to match the order of partition_names.");
+  DEFINE_string(partition_names,
+                string(kLegacyPartitionNameRoot) + ":" +
+                kLegacyPartitionNameKernel,
+                "Names of the partitions. To pass multiple names, use a single "
+                "argument with a colon between names, e.g. "
+                "name:name2:name3:last_name . Name can not be empty, and it "
+                "has to match the order of partitions.");
+  DEFINE_string(in_file, "",
+                "Path to input delta payload file used to hash/sign payloads "
+                "and apply delta over old_image (for debugging)");
+  DEFINE_string(out_file, "", "Path to output delta payload file");
+  DEFINE_string(out_hash_file, "", "Path to output hash file");
+  DEFINE_string(out_metadata_hash_file, "",
+                "Path to output metadata hash file");
+  DEFINE_string(out_metadata_size_file, "",
+                "Path to output metadata size file");
+  DEFINE_string(private_key, "", "Path to private key in .pem format");
+  DEFINE_string(public_key, "", "Path to public key in .pem format");
+  DEFINE_int32(public_key_version, -1,
+               "DEPRECATED. Key-check version # of client");
+  DEFINE_string(prefs_dir, "/tmp/update_engine_prefs",
+                "Preferences directory, used with apply_delta");
+  DEFINE_string(signature_size, "",
+                "Raw signature size used for hash calculation. "
+                "You may pass in multiple sizes by colon separating them. E.g. "
+                "2048:2048:4096 will assume 3 signatures, the first two with "
+                "2048 size and the last 4096.");
+  DEFINE_string(signature_file, "",
+                "Raw signature file to sign payload with. To pass multiple "
+                "signatures, use a single argument with a colon between paths, "
+                "e.g. /path/to/sig:/path/to/next:/path/to/last_sig . Each "
+                "signature will be assigned a client version, starting from "
+                "kSignatureOriginalVersion.");
+  DEFINE_string(metadata_signature_file, "",
+                "Raw signature file with the signature of the metadata hash. "
+                "To pass multiple signatures, use a single argument with a "
+                "colon between paths, "
+                "e.g. /path/to/sig:/path/to/next:/path/to/last_sig .");
+  DEFINE_int32(chunk_size, 200 * 1024 * 1024,
+               "Payload chunk size (-1 for whole files)");
+  DEFINE_uint64(rootfs_partition_size,
+               chromeos_update_engine::kRootFSPartitionSize,
+               "RootFS partition size for the image once installed");
+  DEFINE_uint64(major_version, 1,
+               "The major version of the payload being generated.");
+  DEFINE_int32(minor_version, -1,
+               "The minor version of the payload being generated "
+               "(-1 means autodetect).");
+
+  DEFINE_string(old_channel, "",
+                "The channel for the old image. 'dev-channel', 'npo-channel', "
+                "etc. Ignored, except during delta generation.");
+  DEFINE_string(old_board, "",
+                "The board for the old image. 'x86-mario', 'lumpy', "
+                "etc. Ignored, except during delta generation.");
+  DEFINE_string(old_version, "",
+                "The build version of the old image. 1.2.3, etc.");
+  DEFINE_string(old_key, "",
+                "The key used to sign the old image. 'premp', 'mp', 'mp-v3',"
+                " etc");
+  DEFINE_string(old_build_channel, "",
+                "The channel for the build of the old image. 'dev-channel', "
+                "etc, but will never contain special channels such as "
+                "'npo-channel'. Ignored, except during delta generation.");
+  DEFINE_string(old_build_version, "",
+                "The version of the build containing the old image.");
+
+  DEFINE_string(new_channel, "",
+                "The channel for the new image. 'dev-channel', 'npo-channel', "
+                "etc. Ignored, except during delta generation.");
+  DEFINE_string(new_board, "",
+                "The board for the new image. 'x86-mario', 'lumpy', "
+                "etc. Ignored, except during delta generation.");
+  DEFINE_string(new_version, "",
+                "The build version of the new image. 1.2.3, etc.");
+  DEFINE_string(new_key, "",
+                "The key used to sign the new image. 'premp', 'mp', 'mp-v3',"
+                " etc");
+  DEFINE_string(new_build_channel, "",
+                "The channel for the build of the new image. 'dev-channel', "
+                "etc, but will never contain special channels such as "
+                "'npo-channel'. Ignored, except during delta generation.");
+  DEFINE_string(new_build_version, "",
+                "The version of the build containing the new image.");
+  DEFINE_string(new_postinstall_config_file, "",
+                "A config file specifying postinstall related metadata. "
+                "Only allowed in major version 2 or newer.");
+
+  brillo::FlagHelper::Init(argc, argv,
+      "Generates a payload to provide to ChromeOS' update_engine.\n\n"
+      "This tool can create full payloads and also delta payloads if the src\n"
+      "image is provided. It also provides debugging options to apply, sign\n"
+      "and verify payloads.");
+  Terminator::Init();
+
+  logging::LoggingSettings log_settings;
+  log_settings.log_file     = "delta_generator.log";
+  log_settings.logging_dest = logging::LOG_TO_SYSTEM_DEBUG_LOG;
+  log_settings.lock_log     = logging::LOCK_LOG_FILE;
+  log_settings.delete_old   = logging::APPEND_TO_OLD_LOG_FILE;
+
+  logging::InitLogging(log_settings);
+
+  vector<int> signature_sizes;
+  ParseSignatureSizes(FLAGS_signature_size, &signature_sizes);
+
+  if (!FLAGS_out_hash_file.empty() || !FLAGS_out_metadata_hash_file.empty()) {
+    CHECK(FLAGS_out_metadata_size_file.empty());
+    CalculateHashForSigning(signature_sizes, FLAGS_out_hash_file,
+                            FLAGS_out_metadata_hash_file, FLAGS_in_file);
+    return 0;
+  }
+  if (!FLAGS_signature_file.empty()) {
+    SignPayload(FLAGS_in_file, FLAGS_out_file, FLAGS_signature_file,
+                FLAGS_metadata_signature_file, FLAGS_out_metadata_size_file);
+    return 0;
+  }
+  if (!FLAGS_public_key.empty()) {
+    LOG_IF(WARNING, FLAGS_public_key_version != -1)
+        << "--public_key_version is deprecated and ignored.";
+    VerifySignedPayload(FLAGS_in_file, FLAGS_public_key);
+    return 0;
+  }
+  if (!FLAGS_in_file.empty()) {
+    ApplyDelta(FLAGS_in_file, FLAGS_old_kernel, FLAGS_old_image,
+               FLAGS_prefs_dir);
+    return 0;
+  }
+
+  // A payload generation was requested. Convert the flags to a
+  // PayloadGenerationConfig.
+  PayloadGenerationConfig payload_config;
+  vector<string> partition_names, old_partitions, new_partitions;
+
+  base::SplitString(FLAGS_partition_names, ':', &partition_names);
+  CHECK(!partition_names.empty());
+  if (FLAGS_major_version == kChromeOSMajorPayloadVersion ||
+      FLAGS_new_partitions.empty()) {
+    LOG_IF(FATAL, partition_names.size() != 2)
+        << "To support more than 2 partitions, please use the "
+        << "--new_partitions flag and major version 2.";
+    LOG_IF(FATAL, partition_names[0] != kLegacyPartitionNameRoot ||
+                  partition_names[1] != kLegacyPartitionNameKernel)
+        << "To support non-default partition name, please use the "
+        << "--new_partitions flag and major version 2.";
+  }
+
+  if (!FLAGS_new_partitions.empty()) {
+    LOG_IF(FATAL, !FLAGS_new_image.empty() || !FLAGS_new_kernel.empty())
+        << "--new_image and --new_kernel are deprecated, please use "
+        << "--new_partitions for all partitions.";
+    base::SplitString(FLAGS_new_partitions, ':', &new_partitions);
+    CHECK(partition_names.size() == new_partitions.size());
+
+    payload_config.is_delta = !FLAGS_old_partitions.empty();
+    LOG_IF(FATAL, !FLAGS_old_image.empty() || !FLAGS_old_kernel.empty())
+        << "--old_image and --old_kernel are deprecated, please use "
+        << "--old_partitions if you are using --new_partitions.";
+  } else {
+    new_partitions = {FLAGS_new_image, FLAGS_new_kernel};
+    LOG(WARNING) << "--new_partitions is empty, using deprecated --new_image "
+                 << "and --new_kernel flags.";
+
+    payload_config.is_delta = !FLAGS_old_image.empty() ||
+                              !FLAGS_old_kernel.empty();
+    LOG_IF(FATAL, !FLAGS_old_partitions.empty())
+        << "Please use --new_partitions if you are using --old_partitions.";
+  }
+  for (size_t i = 0; i < partition_names.size(); i++) {
+    LOG_IF(FATAL, partition_names[i].empty())
+        << "Partition name can't be empty, see --partition_names.";
+    payload_config.target.partitions.emplace_back(partition_names[i]);
+    payload_config.target.partitions.back().path = new_partitions[i];
+  }
+
+  if (payload_config.is_delta) {
+    if (!FLAGS_old_partitions.empty()) {
+      base::SplitString(FLAGS_old_partitions, ':', &old_partitions);
+      CHECK(old_partitions.size() == new_partitions.size());
+    } else {
+      old_partitions = {FLAGS_old_image, FLAGS_old_kernel};
+      LOG(WARNING) << "--old_partitions is empty, using deprecated --old_image "
+                   << "and --old_kernel flags.";
+    }
+    for (size_t i = 0; i < partition_names.size(); i++) {
+      payload_config.source.partitions.emplace_back(partition_names[i]);
+      payload_config.source.partitions.back().path = old_partitions[i];
+    }
+  }
+
+  if (!FLAGS_new_postinstall_config_file.empty()) {
+    LOG_IF(FATAL, FLAGS_major_version == kChromeOSMajorPayloadVersion)
+        << "Postinstall config is only allowed in major version 2 or newer.";
+    brillo::KeyValueStore store;
+    CHECK(store.Load(base::FilePath(FLAGS_new_postinstall_config_file)));
+    CHECK(payload_config.target.LoadPostInstallConfig(store));
+  }
+
+  // Use the default soft_chunk_size defined in the config.
+  payload_config.hard_chunk_size = FLAGS_chunk_size;
+  payload_config.block_size = kBlockSize;
+
+  // The partition size is never passed to the delta_generator, so we
+  // need to detect those from the provided files.
+  if (payload_config.is_delta) {
+    CHECK(payload_config.source.LoadImageSize());
+  }
+  CHECK(payload_config.target.LoadImageSize());
+
+  CHECK(!FLAGS_out_file.empty());
+
+  // Ignore failures. These are optional arguments.
+  ParseImageInfo(FLAGS_new_channel,
+                 FLAGS_new_board,
+                 FLAGS_new_version,
+                 FLAGS_new_key,
+                 FLAGS_new_build_channel,
+                 FLAGS_new_build_version,
+                 &payload_config.target.image_info);
+
+  // Ignore failures. These are optional arguments.
+  ParseImageInfo(FLAGS_old_channel,
+                 FLAGS_old_board,
+                 FLAGS_old_version,
+                 FLAGS_old_key,
+                 FLAGS_old_build_channel,
+                 FLAGS_old_build_version,
+                 &payload_config.source.image_info);
+
+  payload_config.rootfs_partition_size = FLAGS_rootfs_partition_size;
+
+  if (payload_config.is_delta) {
+    // Avoid opening the filesystem interface for full payloads.
+    for (PartitionConfig& part : payload_config.target.partitions)
+      CHECK(part.OpenFilesystem());
+    for (PartitionConfig& part : payload_config.source.partitions)
+      CHECK(part.OpenFilesystem());
+  }
+
+  payload_config.major_version = FLAGS_major_version;
+  LOG(INFO) << "Using provided major_version=" << FLAGS_major_version;
+
+  if (FLAGS_minor_version == -1) {
+    // Autodetect minor_version by looking at the update_engine.conf in the old
+    // image.
+    if (payload_config.is_delta) {
+      payload_config.minor_version = kInPlaceMinorPayloadVersion;
+      brillo::KeyValueStore store;
+      uint32_t minor_version;
+      for (const PartitionConfig& part : payload_config.source.partitions) {
+        if (part.fs_interface && part.fs_interface->LoadSettings(&store) &&
+            utils::GetMinorVersion(store, &minor_version)) {
+          payload_config.minor_version = minor_version;
+          break;
+        }
+      }
+    } else {
+      payload_config.minor_version = kFullPayloadMinorVersion;
+    }
+    LOG(INFO) << "Auto-detected minor_version=" << payload_config.minor_version;
+  } else {
+    payload_config.minor_version = FLAGS_minor_version;
+    LOG(INFO) << "Using provided minor_version=" << FLAGS_minor_version;
+  }
+
+  if (payload_config.is_delta) {
+    LOG(INFO) << "Generating delta update";
+  } else {
+    LOG(INFO) << "Generating full update";
+  }
+
+  // From this point, all the options have been parsed.
+  if (!payload_config.Validate()) {
+    LOG(ERROR) << "Invalid options passed. See errors above.";
+    return 1;
+  }
+
+  uint64_t metadata_size;
+  if (!GenerateUpdatePayloadFile(payload_config,
+                                 FLAGS_out_file,
+                                 FLAGS_private_key,
+                                 &metadata_size)) {
+    return 1;
+  }
+  if (!FLAGS_out_metadata_size_file.empty()) {
+    string metadata_size_string = std::to_string(metadata_size);
+    CHECK(utils::WriteFile(FLAGS_out_metadata_size_file.c_str(),
+                           metadata_size_string.data(),
+                           metadata_size_string.size()));
+  }
+  return 0;
+}
+
+}  // namespace
+
+}  // namespace chromeos_update_engine
+
+int main(int argc, char** argv) {
+  return chromeos_update_engine::Main(argc, argv);
+}
diff --git a/payload_generator/graph_types.cc b/payload_generator/graph_types.cc
new file mode 100644
index 0000000..7da76f7
--- /dev/null
+++ b/payload_generator/graph_types.cc
@@ -0,0 +1,23 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/graph_types.h"
+
+namespace chromeos_update_engine {
+
+const Vertex::Index Vertex::kInvalidIndex = static_cast<Vertex::Index>(-1);
+
+}  // chromeos_update_engine
diff --git a/payload_generator/graph_types.h b/payload_generator/graph_types.h
new file mode 100644
index 0000000..beee4eb
--- /dev/null
+++ b/payload_generator/graph_types.h
@@ -0,0 +1,90 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_TYPES_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_TYPES_H_
+
+#include <map>
+#include <set>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/extent_utils.h"
+#include "update_engine/update_metadata.pb.h"
+
+// A few classes that help in generating delta images use these types
+// for the graph work.
+
+namespace chromeos_update_engine {
+
+struct EdgeProperties {
+  // Read-before extents. I.e., blocks in |extents| must be read by the
+  // node pointed to before the pointing node runs (presumably b/c it
+  // overwrites these blocks).
+  std::vector<Extent> extents;
+
+  // Write before extents. I.e., blocks in |write_extents| must be written
+  // by the node pointed to before the pointing node runs (presumably
+  // b/c it reads the data written by the other node).
+  std::vector<Extent> write_extents;
+
+  bool operator==(const EdgeProperties& that) const {
+    return extents == that.extents && write_extents == that.write_extents;
+  }
+};
+
+struct Vertex {
+  Vertex() :
+      valid(true),
+      index(-1),
+      lowlink(-1) {}
+  bool valid;
+
+  typedef std::map<std::vector<Vertex>::size_type, EdgeProperties> EdgeMap;
+  EdgeMap out_edges;
+
+  // We sometimes wish to consider a subgraph of a graph. A subgraph would have
+  // a subset of the vertices from the graph and a subset of the edges.
+  // When considering this vertex within a subgraph, subgraph_edges stores
+  // the out-edges.
+  typedef std::set<std::vector<Vertex>::size_type> SubgraphEdgeMap;
+  SubgraphEdgeMap subgraph_edges;
+
+  // For Tarjan's algorithm:
+  std::vector<Vertex>::size_type index;
+  std::vector<Vertex>::size_type lowlink;
+
+  // Other Vertex properties:
+  AnnotatedOperation aop;
+
+  typedef std::vector<Vertex>::size_type Index;
+  static const Vertex::Index kInvalidIndex;
+};
+
+typedef std::vector<Vertex> Graph;
+
+typedef std::pair<Vertex::Index, Vertex::Index> Edge;
+
+const uint64_t kTempBlockStart = 1ULL << 60;
+COMPILE_ASSERT(kTempBlockStart != 0, kTempBlockStart_invalid);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_TYPES_H_
diff --git a/payload_generator/graph_utils.cc b/payload_generator/graph_utils.cc
new file mode 100644
index 0000000..2d5fb63
--- /dev/null
+++ b/payload_generator/graph_utils.cc
@@ -0,0 +1,141 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_generator/graph_utils.h"
+
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/macros.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using std::make_pair;
+using std::pair;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+namespace graph_utils {
+
+uint64_t EdgeWeight(const Graph& graph, const Edge& edge) {
+  uint64_t weight = 0;
+  const vector<Extent>& extents =
+      graph[edge.first].out_edges.find(edge.second)->second.extents;
+  for (vector<Extent>::const_iterator it = extents.begin();
+       it != extents.end(); ++it) {
+    if (it->start_block() != kSparseHole)
+      weight += it->num_blocks();
+  }
+  return weight;
+}
+
+void AddReadBeforeDep(Vertex* src,
+                      Vertex::Index dst,
+                      uint64_t block) {
+  Vertex::EdgeMap::iterator edge_it = src->out_edges.find(dst);
+  if (edge_it == src->out_edges.end()) {
+    // Must create new edge
+    pair<Vertex::EdgeMap::iterator, bool> result =
+        src->out_edges.insert(make_pair(dst, EdgeProperties()));
+    CHECK(result.second);
+    edge_it = result.first;
+  }
+  AppendBlockToExtents(&edge_it->second.extents, block);
+}
+
+void AddReadBeforeDepExtents(Vertex* src,
+                             Vertex::Index dst,
+                             const vector<Extent>& extents) {
+  // TODO(adlr): Be more efficient than adding each block individually.
+  for (vector<Extent>::const_iterator it = extents.begin(), e = extents.end();
+       it != e; ++it) {
+    const Extent& extent = *it;
+    for (uint64_t block = extent.start_block(),
+             block_end = extent.start_block() + extent.num_blocks();
+         block != block_end; ++block) {
+      AddReadBeforeDep(src, dst, block);
+    }
+  }
+}
+
+void DropWriteBeforeDeps(Vertex::EdgeMap* edge_map) {
+  // Specially crafted for-loop for the map-iterate-delete dance.
+  for (Vertex::EdgeMap::iterator it = edge_map->begin();
+       it != edge_map->end(); ) {
+    if (!it->second.write_extents.empty())
+      it->second.write_extents.clear();
+    if (it->second.extents.empty()) {
+      // Erase *it, as it contains no blocks
+      edge_map->erase(it++);
+    } else {
+      ++it;
+    }
+  }
+}
+
+// For each node N in graph, drop all edges N->|index|.
+void DropIncomingEdgesTo(Graph* graph, Vertex::Index index) {
+  // This would be much more efficient if we had doubly-linked
+  // edges in the graph.
+  for (Graph::iterator it = graph->begin(), e = graph->end(); it != e; ++it) {
+    it->out_edges.erase(index);
+  }
+}
+
+namespace {
+template<typename T>
+void DumpExtents(const T& field, int prepend_space_count) {
+  string header(prepend_space_count, ' ');
+  for (int i = 0, e = field.size(); i != e; ++i) {
+    LOG(INFO) << header << "(" << GetElement(field, i).start_block() << ", "
+              << GetElement(field, i).num_blocks() << ")";
+  }
+}
+
+void DumpOutEdges(const Vertex::EdgeMap& out_edges) {
+  for (Vertex::EdgeMap::const_iterator it = out_edges.begin(),
+           e = out_edges.end(); it != e; ++it) {
+    LOG(INFO) << "    " << it->first << " read-before:";
+    DumpExtents(it->second.extents, 6);
+    LOG(INFO) << "      write-before:";
+    DumpExtents(it->second.write_extents, 6);
+  }
+}
+}  // namespace
+
+void DumpGraph(const Graph& graph) {
+  LOG(INFO) << "Graph length: " << graph.size();
+  for (Graph::size_type i = 0, e = graph.size(); i != e; ++i) {
+    LOG(INFO) << i
+              << (graph[i].valid ? "" : "-INV")
+              << ": " << graph[i].aop.name
+              << ": " << InstallOperationTypeName(graph[i].aop.op.type());
+    LOG(INFO) << "  src_extents:";
+    DumpExtents(graph[i].aop.op.src_extents(), 4);
+    LOG(INFO) << "  dst_extents:";
+    DumpExtents(graph[i].aop.op.dst_extents(), 4);
+    LOG(INFO) << "  out edges:";
+    DumpOutEdges(graph[i].out_edges);
+  }
+}
+
+}  // namespace graph_utils
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/graph_utils.h b/payload_generator/graph_utils.h
new file mode 100644
index 0000000..b32e666
--- /dev/null
+++ b/payload_generator/graph_utils.h
@@ -0,0 +1,56 @@
+//
+// Copyright (C) 2009 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_UTILS_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_UTILS_H_
+
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/payload_generator/graph_types.h"
+#include "update_engine/update_metadata.pb.h"
+
+// A few utility functions for graphs
+
+namespace chromeos_update_engine {
+
+namespace graph_utils {
+
+// Returns the number of blocks represented by all extents in the edge.
+uint64_t EdgeWeight(const Graph& graph, const Edge& edge);
+
+// These add a read-before dependency from graph[src] -> graph[dst]. If the dep
+// already exists, the block/s is/are added to the existing edge.
+void AddReadBeforeDep(Vertex* src,
+                      Vertex::Index dst,
+                      uint64_t block);
+void AddReadBeforeDepExtents(Vertex* src,
+                             Vertex::Index dst,
+                             const std::vector<Extent>& extents);
+
+void DropWriteBeforeDeps(Vertex::EdgeMap* edge_map);
+
+// For each node N in graph, drop all edges N->|index|.
+void DropIncomingEdgesTo(Graph* graph, Vertex::Index index);
+
+void DumpGraph(const Graph& graph);
+
+}  // namespace graph_utils
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_GRAPH_UTILS_H_
diff --git a/payload_generator/graph_utils_unittest.cc b/payload_generator/graph_utils_unittest.cc
new file mode 100644
index 0000000..7d3dbe3
--- /dev/null
+++ b/payload_generator/graph_utils_unittest.cc
@@ -0,0 +1,95 @@
+//
+// Copyright (C) 2009 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 "update_engine/payload_generator/graph_utils.h"
+
+#include <utility>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/extent_utils.h"
+
+using std::make_pair;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class GraphUtilsTest : public ::testing::Test {};
+
+TEST(GraphUtilsTest, SimpleTest) {
+  Graph graph(2);
+
+  graph[0].out_edges.insert(make_pair(1, EdgeProperties()));
+
+  vector<Extent>& extents = graph[0].out_edges[1].extents;
+
+  EXPECT_EQ(0, extents.size());
+  AppendBlockToExtents(&extents, 0);
+  EXPECT_EQ(1, extents.size());
+  AppendBlockToExtents(&extents, 1);
+  AppendBlockToExtents(&extents, 2);
+  EXPECT_EQ(1, extents.size());
+  AppendBlockToExtents(&extents, 4);
+
+  EXPECT_EQ(2, extents.size());
+  EXPECT_EQ(0, extents[0].start_block());
+  EXPECT_EQ(3, extents[0].num_blocks());
+  EXPECT_EQ(4, extents[1].start_block());
+  EXPECT_EQ(1, extents[1].num_blocks());
+
+  EXPECT_EQ(4, graph_utils::EdgeWeight(graph, make_pair(0, 1)));
+}
+
+
+TEST(GraphUtilsTest, DepsTest) {
+  Graph graph(3);
+
+  graph_utils::AddReadBeforeDep(&graph[0], 1, 3);
+  EXPECT_EQ(1, graph[0].out_edges.size());
+  {
+    Extent& extent = graph[0].out_edges[1].extents[0];
+    EXPECT_EQ(3, extent.start_block());
+    EXPECT_EQ(1, extent.num_blocks());
+  }
+  graph_utils::AddReadBeforeDep(&graph[0], 1, 4);
+  EXPECT_EQ(1, graph[0].out_edges.size());
+  {
+    Extent& extent = graph[0].out_edges[1].extents[0];
+    EXPECT_EQ(3, extent.start_block());
+    EXPECT_EQ(2, extent.num_blocks());
+  }
+  graph_utils::AddReadBeforeDepExtents(&graph[2], 1,
+    vector<Extent>(1, ExtentForRange(5, 2)));
+  EXPECT_EQ(1, graph[2].out_edges.size());
+  {
+    Extent& extent = graph[2].out_edges[1].extents[0];
+    EXPECT_EQ(5, extent.start_block());
+    EXPECT_EQ(2, extent.num_blocks());
+  }
+  // Change most recent edge from read-before to write-before
+  graph[2].out_edges[1].write_extents.swap(graph[2].out_edges[1].extents);
+  graph_utils::DropWriteBeforeDeps(&graph[2].out_edges);
+  EXPECT_EQ(0, graph[2].out_edges.size());
+
+  EXPECT_EQ(1, graph[0].out_edges.size());
+  graph_utils::DropIncomingEdgesTo(&graph, 1);
+  EXPECT_EQ(0, graph[0].out_edges.size());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/inplace_generator.cc b/payload_generator/inplace_generator.cc
new file mode 100644
index 0000000..2111748
--- /dev/null
+++ b/payload_generator/inplace_generator.cc
@@ -0,0 +1,823 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/inplace_generator.h"
+
+#include <algorithm>
+#include <map>
+#include <set>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/cycle_breaker.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/delta_diff_utils.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/graph_types.h"
+#include "update_engine/payload_generator/graph_utils.h"
+#include "update_engine/payload_generator/topological_sort.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::make_pair;
+using std::map;
+using std::pair;
+using std::set;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+using Block = InplaceGenerator::Block;
+
+namespace {
+
+// This class allocates non-existent temp blocks, starting from
+// kTempBlockStart. Other code is responsible for converting these
+// temp blocks into real blocks, as the client can't read or write to
+// these blocks.
+class DummyExtentAllocator {
+ public:
+  vector<Extent> Allocate(const uint64_t block_count) {
+    vector<Extent> ret(1);
+    ret[0].set_start_block(next_block_);
+    ret[0].set_num_blocks(block_count);
+    next_block_ += block_count;
+    return ret;
+  }
+
+ private:
+  uint64_t next_block_{kTempBlockStart};
+};
+
+// Takes a vector of blocks and returns an equivalent vector of Extent
+// objects.
+vector<Extent> CompressExtents(const vector<uint64_t>& blocks) {
+  vector<Extent> new_extents;
+  for (uint64_t block : blocks) {
+    AppendBlockToExtents(&new_extents, block);
+  }
+  return new_extents;
+}
+
+// Helper class to compare two operations by start block of the first Extent in
+// their destination extents given the index of the operations in the graph.
+class IndexedInstallOperationsDstComparator {
+ public:
+  explicit IndexedInstallOperationsDstComparator(Graph* graph)
+    : graph_(graph) {}
+
+  // Compares the operations in the vertex a and b of graph_.
+  bool operator()(size_t a, size_t b) const {
+    return diff_utils::CompareAopsByDestination((*graph_)[a].aop,
+                                                (*graph_)[b].aop);
+  }
+
+ private:
+  const Graph* const graph_;
+};
+
+}  // namespace
+
+void InplaceGenerator::CheckGraph(const Graph& graph) {
+  for (const Vertex& v : graph) {
+    CHECK(v.aop.op.has_type());
+  }
+}
+
+void InplaceGenerator::SubstituteBlocks(
+    Vertex* vertex,
+    const vector<Extent>& remove_extents,
+    const vector<Extent>& replace_extents) {
+  // First, expand out the blocks that op reads from
+  vector<uint64_t> read_blocks =
+      ExpandExtents(vertex->aop.op.src_extents());
+  {
+    // Expand remove_extents and replace_extents
+    vector<uint64_t> remove_extents_expanded = ExpandExtents(remove_extents);
+    vector<uint64_t> replace_extents_expanded = ExpandExtents(replace_extents);
+    CHECK_EQ(remove_extents_expanded.size(), replace_extents_expanded.size());
+    map<uint64_t, uint64_t> conversion;
+    for (vector<uint64_t>::size_type i = 0;
+         i < replace_extents_expanded.size(); i++) {
+      conversion[remove_extents_expanded[i]] = replace_extents_expanded[i];
+    }
+    ApplyMap(&read_blocks, conversion);
+    for (auto& edge_prop_pair : vertex->out_edges) {
+      vector<uint64_t> write_before_deps_expanded = ExpandExtents(
+          edge_prop_pair.second.write_extents);
+      ApplyMap(&write_before_deps_expanded, conversion);
+      edge_prop_pair.second.write_extents =
+          CompressExtents(write_before_deps_expanded);
+    }
+  }
+  // Convert read_blocks back to extents
+  vertex->aop.op.clear_src_extents();
+  vector<Extent> new_extents = CompressExtents(read_blocks);
+  StoreExtents(new_extents, vertex->aop.op.mutable_src_extents());
+}
+
+bool InplaceGenerator::CutEdges(Graph* graph,
+                                const set<Edge>& edges,
+                                vector<CutEdgeVertexes>* out_cuts) {
+  DummyExtentAllocator scratch_allocator;
+  vector<CutEdgeVertexes> cuts;
+  cuts.reserve(edges.size());
+
+  uint64_t scratch_blocks_used = 0;
+  for (const Edge& edge : edges) {
+    cuts.resize(cuts.size() + 1);
+    vector<Extent> old_extents =
+        (*graph)[edge.first].out_edges[edge.second].extents;
+    // Choose some scratch space
+    scratch_blocks_used += graph_utils::EdgeWeight(*graph, edge);
+    cuts.back().tmp_extents =
+        scratch_allocator.Allocate(graph_utils::EdgeWeight(*graph, edge));
+    // create vertex to copy original->scratch
+    cuts.back().new_vertex = graph->size();
+    graph->emplace_back();
+    cuts.back().old_src = edge.first;
+    cuts.back().old_dst = edge.second;
+
+    EdgeProperties& cut_edge_properties =
+        (*graph)[edge.first].out_edges.find(edge.second)->second;
+
+    // This should never happen, as we should only be cutting edges between
+    // real file nodes, and write-before relationships are created from
+    // a real file node to a temp copy node:
+    CHECK(cut_edge_properties.write_extents.empty())
+        << "Can't cut edge that has write-before relationship.";
+
+    // make node depend on the copy operation
+    (*graph)[edge.first].out_edges.insert(make_pair(graph->size() - 1,
+                                                    cut_edge_properties));
+
+    // Set src/dst extents and other proto variables for copy operation
+    graph->back().aop.op.set_type(InstallOperation::MOVE);
+    StoreExtents(cut_edge_properties.extents,
+                 graph->back().aop.op.mutable_src_extents());
+    StoreExtents(cuts.back().tmp_extents,
+                 graph->back().aop.op.mutable_dst_extents());
+    graph->back().aop.op.set_src_length(
+        graph_utils::EdgeWeight(*graph, edge) * kBlockSize);
+    graph->back().aop.op.set_dst_length(graph->back().aop.op.src_length());
+
+    // make the dest node read from the scratch space
+    SubstituteBlocks(
+        &((*graph)[edge.second]),
+        (*graph)[edge.first].out_edges[edge.second].extents,
+        cuts.back().tmp_extents);
+
+    // delete the old edge
+    CHECK_EQ(static_cast<Graph::size_type>(1),
+             (*graph)[edge.first].out_edges.erase(edge.second));
+
+    // Add an edge from dst to copy operation
+    EdgeProperties write_before_edge_properties;
+    write_before_edge_properties.write_extents = cuts.back().tmp_extents;
+    (*graph)[edge.second].out_edges.insert(
+        make_pair(graph->size() - 1, write_before_edge_properties));
+  }
+  out_cuts->swap(cuts);
+  return true;
+}
+
+// Creates all the edges for the graph. Writers of a block point to
+// readers of the same block. This is because for an edge A->B, B
+// must complete before A executes.
+void InplaceGenerator::CreateEdges(
+    Graph* graph,
+    const vector<Block>& blocks) {
+  for (vector<Block>::size_type i = 0;
+       i < blocks.size(); i++) {
+    // Blocks with both a reader and writer get an edge
+    if (blocks[i].reader == Vertex::kInvalidIndex ||
+        blocks[i].writer == Vertex::kInvalidIndex)
+      continue;
+    // Don't have a node depend on itself
+    if (blocks[i].reader == blocks[i].writer)
+      continue;
+    // See if there's already an edge we can add onto
+    Vertex::EdgeMap::iterator edge_it =
+        (*graph)[blocks[i].writer].out_edges.find(blocks[i].reader);
+    if (edge_it == (*graph)[blocks[i].writer].out_edges.end()) {
+      // No existing edge. Create one
+      (*graph)[blocks[i].writer].out_edges.insert(
+          make_pair(blocks[i].reader, EdgeProperties()));
+      edge_it = (*graph)[blocks[i].writer].out_edges.find(blocks[i].reader);
+      CHECK(edge_it != (*graph)[blocks[i].writer].out_edges.end());
+    }
+    AppendBlockToExtents(&edge_it->second.extents, i);
+  }
+}
+
+namespace {
+
+class SortCutsByTopoOrderLess {
+ public:
+  explicit SortCutsByTopoOrderLess(
+      const vector<vector<Vertex::Index>::size_type>& table)
+      : table_(table) {}
+  bool operator()(const CutEdgeVertexes& a, const CutEdgeVertexes& b) {
+    return table_[a.old_dst] < table_[b.old_dst];
+  }
+ private:
+  const vector<vector<Vertex::Index>::size_type>& table_;
+};
+
+}  // namespace
+
+void InplaceGenerator::GenerateReverseTopoOrderMap(
+    const vector<Vertex::Index>& op_indexes,
+    vector<vector<Vertex::Index>::size_type>* reverse_op_indexes) {
+  vector<vector<Vertex::Index>::size_type> table(op_indexes.size());
+  for (vector<Vertex::Index>::size_type i = 0, e = op_indexes.size();
+       i != e; ++i) {
+    Vertex::Index node = op_indexes[i];
+    if (table.size() < (node + 1)) {
+      table.resize(node + 1);
+    }
+    table[node] = i;
+  }
+  reverse_op_indexes->swap(table);
+}
+
+void InplaceGenerator::SortCutsByTopoOrder(
+    const vector<Vertex::Index>& op_indexes,
+    vector<CutEdgeVertexes>* cuts) {
+  // first, make a reverse lookup table.
+  vector<vector<Vertex::Index>::size_type> table;
+  GenerateReverseTopoOrderMap(op_indexes, &table);
+  SortCutsByTopoOrderLess less(table);
+  sort(cuts->begin(), cuts->end(), less);
+}
+
+void InplaceGenerator::MoveAndSortFullOpsToBack(
+    Graph* graph,
+    vector<Vertex::Index>* op_indexes) {
+  vector<Vertex::Index> ret;
+  vector<Vertex::Index> full_ops;
+  ret.reserve(op_indexes->size());
+  for (auto op_index : *op_indexes) {
+    InstallOperation_Type type = (*graph)[op_index].aop.op.type();
+    if (type == InstallOperation::REPLACE ||
+        type == InstallOperation::REPLACE_BZ) {
+      full_ops.push_back(op_index);
+    } else {
+      ret.push_back(op_index);
+    }
+  }
+  LOG(INFO) << "Stats: " << full_ops.size() << " full ops out of "
+            << (full_ops.size() + ret.size()) << " total ops.";
+  // Sort full ops according to their dst_extents.
+  sort(full_ops.begin(), full_ops.end(),
+       IndexedInstallOperationsDstComparator(graph));
+  ret.insert(ret.end(), full_ops.begin(), full_ops.end());
+  op_indexes->swap(ret);
+}
+
+namespace {
+
+template<typename T>
+bool TempBlocksExistInExtents(const T& extents) {
+  for (int i = 0, e = extents.size(); i < e; ++i) {
+    Extent extent = GetElement(extents, i);
+    uint64_t start = extent.start_block();
+    uint64_t num = extent.num_blocks();
+    if (start >= kTempBlockStart || (start + num) >= kTempBlockStart) {
+      LOG(ERROR) << "temp block!";
+      LOG(ERROR) << "start: " << start << ", num: " << num;
+      LOG(ERROR) << "kTempBlockStart: " << kTempBlockStart;
+      LOG(ERROR) << "returning true";
+      return true;
+    }
+    // check for wrap-around, which would be a bug:
+    CHECK(start <= (start + num));
+  }
+  return false;
+}
+
+// Converts the cuts, which must all have the same |old_dst| member,
+// to full. It does this by converting the |old_dst| to REPLACE or
+// REPLACE_BZ, dropping all incoming edges to |old_dst|, and marking
+// all temp nodes invalid.
+bool ConvertCutsToFull(
+    Graph* graph,
+    const string& new_part,
+    BlobFileWriter* blob_file,
+    vector<Vertex::Index>* op_indexes,
+    vector<vector<Vertex::Index>::size_type>* reverse_op_indexes,
+    const vector<CutEdgeVertexes>& cuts) {
+  CHECK(!cuts.empty());
+  set<Vertex::Index> deleted_nodes;
+  for (const CutEdgeVertexes& cut : cuts) {
+    TEST_AND_RETURN_FALSE(InplaceGenerator::ConvertCutToFullOp(
+        graph,
+        cut,
+        new_part,
+        blob_file));
+    deleted_nodes.insert(cut.new_vertex);
+  }
+  deleted_nodes.insert(cuts[0].old_dst);
+
+  vector<Vertex::Index> new_op_indexes;
+  new_op_indexes.reserve(op_indexes->size());
+  for (Vertex::Index vertex_index : *op_indexes) {
+    if (utils::SetContainsKey(deleted_nodes, vertex_index))
+      continue;
+    new_op_indexes.push_back(vertex_index);
+  }
+  new_op_indexes.push_back(cuts[0].old_dst);
+  op_indexes->swap(new_op_indexes);
+  InplaceGenerator::GenerateReverseTopoOrderMap(*op_indexes,
+                                                reverse_op_indexes);
+  return true;
+}
+
+// Tries to assign temp blocks for a collection of cuts, all of which share
+// the same old_dst member. If temp blocks can't be found, old_dst will be
+// converted to a REPLACE or REPLACE_BZ operation. Returns true on success,
+// which can happen even if blocks are converted to full. Returns false
+// on exceptional error cases.
+bool AssignBlockForAdjoiningCuts(
+    Graph* graph,
+    const string& new_part,
+    BlobFileWriter* blob_file,
+    vector<Vertex::Index>* op_indexes,
+    vector<vector<Vertex::Index>::size_type>* reverse_op_indexes,
+    const vector<CutEdgeVertexes>& cuts) {
+  CHECK(!cuts.empty());
+  const Vertex::Index old_dst = cuts[0].old_dst;
+  // Calculate # of blocks needed
+  uint64_t blocks_needed = 0;
+  vector<uint64_t> cuts_blocks_needed(cuts.size());
+  for (vector<CutEdgeVertexes>::size_type i = 0; i < cuts.size(); ++i) {
+    uint64_t cut_blocks_needed = 0;
+    for (const Extent& extent : cuts[i].tmp_extents) {
+      cut_blocks_needed += extent.num_blocks();
+    }
+    blocks_needed += cut_blocks_needed;
+    cuts_blocks_needed[i] = cut_blocks_needed;
+  }
+
+  // Find enough blocks
+  ExtentRanges scratch_ranges;
+  // Each block that's supplying temp blocks and the corresponding blocks:
+  typedef vector<pair<Vertex::Index, ExtentRanges>> SupplierVector;
+  SupplierVector block_suppliers;
+  uint64_t scratch_blocks_found = 0;
+  for (vector<Vertex::Index>::size_type i = (*reverse_op_indexes)[old_dst] + 1,
+           e = op_indexes->size(); i < e; ++i) {
+    Vertex::Index test_node = (*op_indexes)[i];
+    if (!(*graph)[test_node].valid)
+      continue;
+    // See if this node has sufficient blocks
+    ExtentRanges ranges;
+    ranges.AddRepeatedExtents((*graph)[test_node].aop.op.dst_extents());
+    ranges.SubtractExtent(ExtentForRange(
+        kTempBlockStart, kSparseHole - kTempBlockStart));
+    ranges.SubtractRepeatedExtents((*graph)[test_node].aop.op.src_extents());
+    // For now, for simplicity, subtract out all blocks in read-before
+    // dependencies.
+    for (Vertex::EdgeMap::const_iterator edge_i =
+             (*graph)[test_node].out_edges.begin(),
+             edge_e = (*graph)[test_node].out_edges.end();
+         edge_i != edge_e; ++edge_i) {
+      ranges.SubtractExtents(edge_i->second.extents);
+    }
+
+    // Prevent using the block 0 as scratch space due to crbug.com/480751.
+    if (ranges.ContainsBlock(0)) {
+      LOG(INFO) << "Removing block 0 from the selected scratch range in vertex "
+                << i;
+      ranges.SubtractBlock(0);
+    }
+
+    if (ranges.blocks() == 0)
+      continue;
+
+    if (ranges.blocks() + scratch_blocks_found > blocks_needed) {
+      // trim down ranges
+      vector<Extent> new_ranges = ranges.GetExtentsForBlockCount(
+          blocks_needed - scratch_blocks_found);
+      ranges = ExtentRanges();
+      ranges.AddExtents(new_ranges);
+    }
+    scratch_ranges.AddRanges(ranges);
+    block_suppliers.push_back(make_pair(test_node, ranges));
+    scratch_blocks_found += ranges.blocks();
+    if (scratch_ranges.blocks() >= blocks_needed)
+      break;
+  }
+  if (scratch_ranges.blocks() < blocks_needed) {
+    LOG(INFO) << "Unable to find sufficient scratch";
+    TEST_AND_RETURN_FALSE(ConvertCutsToFull(graph,
+                                            new_part,
+                                            blob_file,
+                                            op_indexes,
+                                            reverse_op_indexes,
+                                            cuts));
+    return true;
+  }
+  // Use the scratch we found
+  TEST_AND_RETURN_FALSE(scratch_ranges.blocks() == scratch_blocks_found);
+
+  // Make all the suppliers depend on this node
+  for (const auto& index_range_pair : block_suppliers) {
+    graph_utils::AddReadBeforeDepExtents(
+        &(*graph)[index_range_pair.first],
+        old_dst,
+        index_range_pair.second.GetExtentsForBlockCount(
+            index_range_pair.second.blocks()));
+  }
+
+  // Replace temp blocks in each cut
+  for (vector<CutEdgeVertexes>::size_type i = 0; i < cuts.size(); ++i) {
+    const CutEdgeVertexes& cut = cuts[i];
+    vector<Extent> real_extents =
+        scratch_ranges.GetExtentsForBlockCount(cuts_blocks_needed[i]);
+    scratch_ranges.SubtractExtents(real_extents);
+
+    // Fix the old dest node w/ the real blocks
+    InplaceGenerator::SubstituteBlocks(&(*graph)[old_dst],
+                                         cut.tmp_extents,
+                                         real_extents);
+
+    // Fix the new node w/ the real blocks. Since the new node is just a
+    // copy operation, we can replace all the dest extents w/ the real
+    // blocks.
+    InstallOperation* op = &(*graph)[cut.new_vertex].aop.op;
+    op->clear_dst_extents();
+    StoreExtents(real_extents, op->mutable_dst_extents());
+  }
+  return true;
+}
+
+}  // namespace
+
+bool InplaceGenerator::AssignTempBlocks(
+    Graph* graph,
+    const string& new_part,
+    BlobFileWriter* blob_file,
+    vector<Vertex::Index>* op_indexes,
+    vector<vector<Vertex::Index>::size_type>* reverse_op_indexes,
+    const vector<CutEdgeVertexes>& cuts) {
+  CHECK(!cuts.empty());
+
+  // group of cuts w/ the same old_dst:
+  vector<CutEdgeVertexes> cuts_group;
+
+  for (vector<CutEdgeVertexes>::size_type i = cuts.size() - 1, e = 0;
+       true ; --i) {
+    LOG(INFO) << "Fixing temp blocks in cut " << i
+              << ": old dst: " << cuts[i].old_dst << " new vertex: "
+              << cuts[i].new_vertex << " path: "
+              << (*graph)[cuts[i].old_dst].aop.name;
+
+    if (cuts_group.empty() || (cuts_group[0].old_dst == cuts[i].old_dst)) {
+      cuts_group.push_back(cuts[i]);
+    } else {
+      CHECK(!cuts_group.empty());
+      TEST_AND_RETURN_FALSE(AssignBlockForAdjoiningCuts(graph,
+                                                        new_part,
+                                                        blob_file,
+                                                        op_indexes,
+                                                        reverse_op_indexes,
+                                                        cuts_group));
+      cuts_group.clear();
+      cuts_group.push_back(cuts[i]);
+    }
+
+    if (i == e) {
+      // break out of for() loop
+      break;
+    }
+  }
+  CHECK(!cuts_group.empty());
+  TEST_AND_RETURN_FALSE(AssignBlockForAdjoiningCuts(graph,
+                                                    new_part,
+                                                    blob_file,
+                                                    op_indexes,
+                                                    reverse_op_indexes,
+                                                    cuts_group));
+  return true;
+}
+
+bool InplaceGenerator::NoTempBlocksRemain(const Graph& graph) {
+  size_t idx = 0;
+  for (Graph::const_iterator it = graph.begin(), e = graph.end(); it != e;
+       ++it, ++idx) {
+    if (!it->valid)
+      continue;
+    const InstallOperation& op = it->aop.op;
+    if (TempBlocksExistInExtents(op.dst_extents()) ||
+        TempBlocksExistInExtents(op.src_extents())) {
+      LOG(INFO) << "bad extents in node " << idx;
+      LOG(INFO) << "so yeah";
+      return false;
+    }
+
+    // Check out-edges:
+    for (const auto& edge_prop_pair : it->out_edges) {
+      if (TempBlocksExistInExtents(edge_prop_pair.second.extents) ||
+          TempBlocksExistInExtents(edge_prop_pair.second.write_extents)) {
+        LOG(INFO) << "bad out edge in node " << idx;
+        LOG(INFO) << "so yeah";
+        return false;
+      }
+    }
+  }
+  return true;
+}
+
+bool InplaceGenerator::ConvertCutToFullOp(Graph* graph,
+                                          const CutEdgeVertexes& cut,
+                                          const string& new_part,
+                                          BlobFileWriter* blob_file) {
+  // Drop all incoming edges, keep all outgoing edges
+
+  // Keep all outgoing edges
+  if ((*graph)[cut.old_dst].aop.op.type() != InstallOperation::REPLACE_BZ &&
+      (*graph)[cut.old_dst].aop.op.type() != InstallOperation::REPLACE) {
+    Vertex::EdgeMap out_edges = (*graph)[cut.old_dst].out_edges;
+    graph_utils::DropWriteBeforeDeps(&out_edges);
+
+    // Replace the operation with a REPLACE or REPLACE_BZ to generate the same
+    // |new_extents| list of blocks and update the graph.
+    vector<AnnotatedOperation> new_aop;
+    vector<Extent> new_extents;
+    ExtentsToVector((*graph)[cut.old_dst].aop.op.dst_extents(),
+                    &new_extents);
+    TEST_AND_RETURN_FALSE(diff_utils::DeltaReadFile(
+        &new_aop,
+        "",  // old_part
+        new_part,
+        vector<Extent>(),  // old_extents
+        new_extents,
+        (*graph)[cut.old_dst].aop.name,
+        -1,  // chunk_blocks, forces to have a single operation.
+        blob_file,
+        false));  // src_ops_allowed
+    TEST_AND_RETURN_FALSE(new_aop.size() == 1);
+    TEST_AND_RETURN_FALSE(AddInstallOpToGraph(
+      graph, cut.old_dst, nullptr, new_aop.front().op, new_aop.front().name));
+
+    (*graph)[cut.old_dst].out_edges = out_edges;
+
+    // Right now we don't have doubly-linked edges, so we have to scan
+    // the whole graph.
+    graph_utils::DropIncomingEdgesTo(graph, cut.old_dst);
+  }
+
+  // Delete temp node
+  (*graph)[cut.old_src].out_edges.erase(cut.new_vertex);
+  CHECK((*graph)[cut.old_dst].out_edges.find(cut.new_vertex) ==
+        (*graph)[cut.old_dst].out_edges.end());
+  (*graph)[cut.new_vertex].valid = false;
+  LOG(INFO) << "marked node invalid: " << cut.new_vertex;
+  return true;
+}
+
+bool InplaceGenerator::ConvertGraphToDag(Graph* graph,
+                                         const string& new_part,
+                                         BlobFileWriter* blob_file,
+                                         vector<Vertex::Index>* final_order,
+                                         Vertex::Index scratch_vertex) {
+  CycleBreaker cycle_breaker;
+  LOG(INFO) << "Finding cycles...";
+  set<Edge> cut_edges;
+  cycle_breaker.BreakCycles(*graph, &cut_edges);
+  LOG(INFO) << "done finding cycles";
+  CheckGraph(*graph);
+
+  // Calculate number of scratch blocks needed
+
+  LOG(INFO) << "Cutting cycles...";
+  vector<CutEdgeVertexes> cuts;
+  TEST_AND_RETURN_FALSE(CutEdges(graph, cut_edges, &cuts));
+  LOG(INFO) << "done cutting cycles";
+  LOG(INFO) << "There are " << cuts.size() << " cuts.";
+  CheckGraph(*graph);
+
+  LOG(INFO) << "Creating initial topological order...";
+  TopologicalSort(*graph, final_order);
+  LOG(INFO) << "done with initial topo order";
+  CheckGraph(*graph);
+
+  LOG(INFO) << "Moving full ops to the back";
+  MoveAndSortFullOpsToBack(graph, final_order);
+  LOG(INFO) << "done moving full ops to back";
+
+  vector<vector<Vertex::Index>::size_type> inverse_final_order;
+  GenerateReverseTopoOrderMap(*final_order, &inverse_final_order);
+
+  SortCutsByTopoOrder(*final_order, &cuts);
+
+  if (!cuts.empty())
+    TEST_AND_RETURN_FALSE(AssignTempBlocks(graph,
+                                           new_part,
+                                           blob_file,
+                                           final_order,
+                                           &inverse_final_order,
+                                           cuts));
+  LOG(INFO) << "Making sure all temp blocks have been allocated";
+
+  // Remove the scratch node, if any
+  if (scratch_vertex != Vertex::kInvalidIndex) {
+    final_order->erase(final_order->begin() +
+                       inverse_final_order[scratch_vertex]);
+    (*graph)[scratch_vertex].valid = false;
+    GenerateReverseTopoOrderMap(*final_order, &inverse_final_order);
+  }
+
+  graph_utils::DumpGraph(*graph);
+  CHECK(NoTempBlocksRemain(*graph));
+  LOG(INFO) << "done making sure all temp blocks are allocated";
+  return true;
+}
+
+void InplaceGenerator::CreateScratchNode(uint64_t start_block,
+                                         uint64_t num_blocks,
+                                         Vertex* vertex) {
+  vertex->aop.name = "<scratch>";
+  vertex->aop.op.set_type(InstallOperation::REPLACE_BZ);
+  vertex->aop.op.set_data_offset(0);
+  vertex->aop.op.set_data_length(0);
+  Extent* extent = vertex->aop.op.add_dst_extents();
+  extent->set_start_block(start_block);
+  extent->set_num_blocks(num_blocks);
+}
+
+bool InplaceGenerator::AddInstallOpToBlocksVector(
+    const InstallOperation& operation,
+    const Graph& graph,
+    Vertex::Index vertex,
+    vector<Block>* blocks) {
+  // See if this is already present.
+  TEST_AND_RETURN_FALSE(operation.dst_extents_size() > 0);
+
+  enum BlockField { READER = 0, WRITER, BLOCK_FIELD_COUNT };
+  for (int field = READER; field < BLOCK_FIELD_COUNT; field++) {
+    const int extents_size =
+        (field == READER) ? operation.src_extents_size() :
+        operation.dst_extents_size();
+    const char* past_participle = (field == READER) ? "read" : "written";
+    const google::protobuf::RepeatedPtrField<Extent>& extents =
+        (field == READER) ? operation.src_extents() : operation.dst_extents();
+    Vertex::Index Block::*access_type = (field == READER) ?
+        &Block::reader : &Block::writer;
+
+    for (int i = 0; i < extents_size; i++) {
+      const Extent& extent = extents.Get(i);
+      for (uint64_t block = extent.start_block();
+           block < (extent.start_block() + extent.num_blocks()); block++) {
+        if ((*blocks)[block].*access_type != Vertex::kInvalidIndex) {
+          LOG(FATAL) << "Block " << block << " is already "
+                     << past_participle << " by "
+                     << (*blocks)[block].*access_type << "("
+                     << graph[(*blocks)[block].*access_type].aop.name
+                     << ") and also " << vertex << "("
+                     << graph[vertex].aop.name << ")";
+        }
+        (*blocks)[block].*access_type = vertex;
+      }
+    }
+  }
+  return true;
+}
+
+bool InplaceGenerator::AddInstallOpToGraph(Graph* graph,
+                                           Vertex::Index existing_vertex,
+                                           vector<Block>* blocks,
+                                           const InstallOperation operation,
+                                           const string& op_name) {
+  Vertex::Index vertex = existing_vertex;
+  if (vertex == Vertex::kInvalidIndex) {
+    graph->emplace_back();
+    vertex = graph->size() - 1;
+  }
+  (*graph)[vertex].aop.op = operation;
+  CHECK((*graph)[vertex].aop.op.has_type());
+  (*graph)[vertex].aop.name = op_name;
+
+  if (blocks)
+    TEST_AND_RETURN_FALSE(InplaceGenerator::AddInstallOpToBlocksVector(
+        (*graph)[vertex].aop.op,
+        *graph,
+        vertex,
+        blocks));
+  return true;
+}
+
+void InplaceGenerator::ApplyMap(vector<uint64_t>* collection,
+                                const map<uint64_t, uint64_t>& the_map) {
+  for (uint64_t& elem : *collection) {
+    const auto& map_it = the_map.find(elem);
+    if (map_it != the_map.end())
+      elem = map_it->second;
+  }
+}
+
+bool InplaceGenerator::ResolveReadAfterWriteDependencies(
+    const PartitionConfig& new_part,
+    uint64_t partition_size,
+    size_t block_size,
+    BlobFileWriter* blob_file,
+    vector<AnnotatedOperation>* aops) {
+  // Convert the operations to the graph.
+  Graph graph;
+  CheckGraph(graph);
+  vector<Block> blocks(new_part.size / block_size);
+  for (const auto& aop : *aops) {
+    AddInstallOpToGraph(
+        &graph, Vertex::kInvalidIndex, &blocks, aop.op, aop.name);
+  }
+  CheckGraph(graph);
+
+  // Final scratch block (if there's space)
+  Vertex::Index scratch_vertex = Vertex::kInvalidIndex;
+  if (blocks.size() < (partition_size / block_size)) {
+    scratch_vertex = graph.size();
+    graph.emplace_back();
+    size_t scratch_blocks = (partition_size / block_size) - blocks.size();
+    LOG(INFO) << "Added " << scratch_blocks << " scratch space blocks.";
+    CreateScratchNode(blocks.size(), scratch_blocks, &graph.back());
+  }
+  CheckGraph(graph);
+
+  LOG(INFO) << "Creating edges...";
+  CreateEdges(&graph, blocks);
+  LOG(INFO) << "Done creating edges";
+  CheckGraph(graph);
+
+  vector<Vertex::Index> final_order;
+  TEST_AND_RETURN_FALSE(ConvertGraphToDag(
+      &graph,
+      new_part.path,
+      blob_file,
+      &final_order,
+      scratch_vertex));
+
+  // Copy operations over to the |aops| vector in the final_order generated by
+  // the topological sort.
+  aops->clear();
+  aops->reserve(final_order.size());
+  for (const Vertex::Index vertex_index : final_order) {
+    const Vertex& vertex = graph[vertex_index];
+    aops->push_back(vertex.aop);
+  }
+  return true;
+}
+
+bool InplaceGenerator::GenerateOperations(
+    const PayloadGenerationConfig& config,
+    const PartitionConfig& old_part,
+    const PartitionConfig& new_part,
+    BlobFileWriter* blob_file,
+    vector<AnnotatedOperation>* aops) {
+  TEST_AND_RETURN_FALSE(old_part.name == new_part.name);
+
+  ssize_t hard_chunk_blocks = (config.hard_chunk_size == -1 ? -1 :
+                               config.hard_chunk_size / config.block_size);
+  size_t soft_chunk_blocks = config.soft_chunk_size / config.block_size;
+  uint64_t partition_size = new_part.size;
+  if (new_part.name == kLegacyPartitionNameRoot)
+    partition_size = config.rootfs_partition_size;
+
+  LOG(INFO) << "Delta compressing " << new_part.name << " partition...";
+  TEST_AND_RETURN_FALSE(
+    diff_utils::DeltaReadPartition(aops,
+                                   old_part,
+                                   new_part,
+                                   hard_chunk_blocks,
+                                   soft_chunk_blocks,
+                                   blob_file,
+                                   false));  // src_ops_allowed
+  LOG(INFO) << "Done reading " << new_part.name;
+
+  TEST_AND_RETURN_FALSE(
+    ResolveReadAfterWriteDependencies(new_part,
+                                      partition_size,
+                                      config.block_size,
+                                      blob_file,
+                                      aops));
+  LOG(INFO) << "Done reordering " << new_part.name;
+  return true;
+}
+
+};  // namespace chromeos_update_engine
diff --git a/payload_generator/inplace_generator.h b/payload_generator/inplace_generator.h
new file mode 100644
index 0000000..4839824
--- /dev/null
+++ b/payload_generator/inplace_generator.h
@@ -0,0 +1,242 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_INPLACE_GENERATOR_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_INPLACE_GENERATOR_H_
+
+#include <map>
+#include <set>
+#include <string>
+#include <vector>
+
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/graph_types.h"
+#include "update_engine/payload_generator/operations_generator.h"
+
+// InplaceGenerator contains all functionality related to the inplace algorithm
+// for generating update payloads. These are the functions used when delta minor
+// version is 1.
+
+namespace chromeos_update_engine {
+
+// This struct stores all relevant info for an edge that is cut between
+// nodes old_src -> old_dst by creating new vertex new_vertex. The new
+// relationship is:
+// old_src -(read before)-> new_vertex <-(write before)- old_dst
+// new_vertex is a MOVE operation that moves some existing blocks into
+// temp space. The temp extents are, by necessity, stored in new_vertex
+// (as dst extents) and old_dst (as src extents), but they are also broken
+// out into tmp_extents, as the nodes themselves may contain many more
+// extents.
+struct CutEdgeVertexes {
+  Vertex::Index new_vertex;
+  Vertex::Index old_src;
+  Vertex::Index old_dst;
+  std::vector<Extent> tmp_extents;
+};
+
+class InplaceGenerator : public OperationsGenerator {
+ public:
+  // Represents a disk block on the install partition.
+  struct Block {
+    // During install, each block on the install partition will be written
+    // and some may be read (in all likelihood, many will be read).
+    // The reading and writing will be performed by InstallOperations,
+    // each of which has a corresponding vertex in a graph.
+    // A Block object tells which vertex will read or write this block
+    // at install time.
+    // Generally, there will be a vector of Block objects whose length
+    // is the number of blocks on the install partition.
+    Block() : reader(Vertex::kInvalidIndex), writer(Vertex::kInvalidIndex) {}
+    Vertex::Index reader;
+    Vertex::Index writer;
+  };
+
+  InplaceGenerator() = default;
+
+  // Checks all the operations in the graph have a type assigned.
+  static void CheckGraph(const Graph& graph);
+
+  // Modifies blocks read by 'op' so that any blocks referred to by
+  // 'remove_extents' are replaced with blocks from 'replace_extents'.
+  // 'remove_extents' and 'replace_extents' must be the same number of blocks.
+  // Blocks will be substituted in the order listed in the vectors.
+  // E.g. if 'op' reads blocks 1, 2, 3, 4, 5, 6, 7, 8, remove_extents
+  // contains blocks 6, 2, 3, 5, and replace blocks contains
+  // 12, 13, 14, 15, then op will be changed to read from:
+  // 1, 13, 14, 4, 15, 12, 7, 8
+  static void SubstituteBlocks(Vertex* vertex,
+                               const std::vector<Extent>& remove_extents,
+                               const std::vector<Extent>& replace_extents);
+
+  // Cuts 'edges' from 'graph' according to the AU algorithm. This means
+  // for each edge A->B, remove the dependency that B occur before A.
+  // Do this by creating a new operation X that copies from the blocks
+  // specified by the edge's properties to temp space T. Modify B to read
+  // from T rather than the blocks in the edge. Modify A to depend on X,
+  // but not on B. Free space is found by looking in 'blocks'.
+  // Returns true on success.
+  static bool CutEdges(Graph* graph,
+                       const std::set<Edge>& edges,
+                       std::vector<CutEdgeVertexes>* out_cuts);
+
+  // Creates all the edges for the graph. Writers of a block point to
+  // readers of the same block. This is because for an edge A->B, B
+  // must complete before A executes.
+  static void CreateEdges(Graph* graph,
+                          const std::vector<Block>& blocks);
+
+  // Takes |op_indexes|, which is effectively a mapping from order in
+  // which the op is performed -> graph vertex index, and produces the
+  // reverse: a mapping from graph vertex index -> op_indexes index.
+  static void GenerateReverseTopoOrderMap(
+      const std::vector<Vertex::Index>& op_indexes,
+      std::vector<std::vector<Vertex::Index>::size_type>* reverse_op_indexes);
+
+  // Sorts the vector |cuts| by its |cuts[].old_dest| member. Order is
+  // determined by the order of elements in op_indexes.
+  static void SortCutsByTopoOrder(
+      const std::vector<Vertex::Index>& op_indexes,
+      std::vector<CutEdgeVertexes>* cuts);
+
+  // Given a topologically sorted graph |op_indexes| and |graph|, alters
+  // |op_indexes| to move all the full operations to the end of the vector.
+  // Full operations should not be depended on, so this is safe.
+  static void MoveAndSortFullOpsToBack(Graph* graph,
+                                std::vector<Vertex::Index>* op_indexes);
+
+  // Returns true iff there are no extents in the graph that refer to temp
+  // blocks. Temp blocks are in the range [kTempBlockStart, kSparseHole).
+  static bool NoTempBlocksRemain(const Graph& graph);
+
+  // Takes a |graph|, which has edges that must be cut, as listed in
+  // |cuts|.  Cuts the edges. Maintains a list in which the operations
+  // will be performed (in |op_indexes|) and the reverse (in
+  // |reverse_op_indexes|).  Cutting edges requires scratch space, and
+  // if insufficient scratch is found, the file is reread and will be
+  // send down (either as REPLACE or REPLACE_BZ).  Returns true on
+  // success.
+  static bool AssignTempBlocks(
+      Graph* graph,
+      const std::string& new_part,
+      BlobFileWriter* blob_file,
+      std::vector<Vertex::Index>* op_indexes,
+      std::vector<std::vector<Vertex::Index>::size_type>* reverse_op_indexes,
+      const std::vector<CutEdgeVertexes>& cuts);
+
+  // Handles allocation of temp blocks to a cut edge by converting the
+  // dest node to a full op. This removes the need for temp blocks, but
+  // comes at the cost of a worse compression ratio.
+  // For example, say we have A->B->A. It would first be cut to form:
+  // A->B->N<-A, where N copies blocks to temp space. If there are no
+  // temp blocks, this function can be called to convert it to the form:
+  // A->B. Now, A is a full operation.
+  static bool ConvertCutToFullOp(Graph* graph,
+                                 const CutEdgeVertexes& cut,
+                                 const std::string& new_part,
+                                 BlobFileWriter* blob_file);
+
+  // Takes a graph, which is not a DAG, which represents the files just
+  // read from disk, and converts it into a DAG by breaking all cycles
+  // and finding temp space to resolve broken edges.
+  // The final order of the nodes is given in |final_order|
+  // Some files may need to be reread from disk, thus |fd| and
+  // |data_file_size| are be passed.
+  // If |scratch_vertex| is not kInvalidIndex, removes it from
+  // |final_order| before returning.
+  // Returns true on success.
+  static bool ConvertGraphToDag(Graph* graph,
+                                const std::string& new_part,
+                                BlobFileWriter* blob_file,
+                                std::vector<Vertex::Index>* final_order,
+                                Vertex::Index scratch_vertex);
+
+  // Creates a dummy REPLACE_BZ node in the given |vertex|. This can be used
+  // to provide scratch space. The node writes |num_blocks| blocks starting at
+  // |start_block|The node should be marked invalid before writing all nodes to
+  // the output file.
+  static void CreateScratchNode(uint64_t start_block,
+                                uint64_t num_blocks,
+                                Vertex* vertex);
+
+  // The |blocks| vector contains a reader and writer for each block on the
+  // filesystem that's being in-place updated. We populate the reader/writer
+  // fields of |blocks| by calling this function.
+  // For each block in |operation| that is read or written, find that block
+  // in |blocks| and set the reader/writer field to the vertex passed.
+  // |graph| is not strictly necessary, but useful for printing out
+  // error messages.
+  static bool AddInstallOpToBlocksVector(const InstallOperation& operation,
+                                         const Graph& graph,
+                                         Vertex::Index vertex,
+                                         std::vector<Block>* blocks);
+
+  // Add a vertex (if |existing_vertex| is kInvalidVertex) or update an
+  // |existing_vertex| with the passed |operation|.
+  // This method will also register the vertex as the reader or writer of the
+  // blocks involved in the operation updating the |blocks| vector. The
+  // |op_name| associated with the Vertex is used for logging purposes.
+  static bool AddInstallOpToGraph(Graph* graph,
+                                  Vertex::Index existing_vertex,
+                                  std::vector<Block>* blocks,
+                                  const InstallOperation operation,
+                                  const std::string& op_name);
+
+  // Apply the transformation stored in |the_map| to the |collection| vector
+  // replacing the map keys found in |collection| with its associated value in
+  // |the_map|.
+  static void ApplyMap(std::vector<uint64_t>* collection,
+                       const std::map<uint64_t, uint64_t>& the_map);
+
+  // Resolve all read-after-write dependencies in the operation list |aops|. The
+  // operations in |aops| are such that they generate the desired |new_part| if
+  // applied reading always from the original image. This function reorders the
+  // operations and generates new operations when needed to make these
+  // operations produce the same |new_part| result when applied in-place.
+  // The new operations will create blobs in |data_file_fd| and update
+  // the file size pointed by |data_file_size| if needed.
+  // On success, stores the new operations in |aops| in the right order and
+  // returns true.
+  static bool ResolveReadAfterWriteDependencies(
+      const PartitionConfig& new_part,
+      uint64_t partition_size,
+      size_t block_size,
+      BlobFileWriter* blob_file,
+      std::vector<AnnotatedOperation>* aops);
+
+  // Generate the update payload operations for the given partition using
+  // only operations that read from the target and/or write to the target,
+  // hence, applying the payload "in-place" in the target partition. This method
+  // assumes that the contents of the source image are pre-copied to the target
+  // partition, up to the size of the source image. Use this method to generate
+  // a delta update with the minor version kInPlaceMinorPayloadVersion.
+  // The operations are stored in |aops|. All the offsets in the operations
+  // reference the data written to |blob_file|.
+  bool GenerateOperations(
+      const PayloadGenerationConfig& config,
+      const PartitionConfig& old_part,
+      const PartitionConfig& new_part,
+      BlobFileWriter* blob_file,
+      std::vector<AnnotatedOperation>* aops) override;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(InplaceGenerator);
+};
+
+};  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_INPLACE_GENERATOR_H_
diff --git a/payload_generator/inplace_generator_unittest.cc b/payload_generator/inplace_generator_unittest.cc
new file mode 100644
index 0000000..9932ef9
--- /dev/null
+++ b/payload_generator/inplace_generator_unittest.cc
@@ -0,0 +1,658 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/inplace_generator.h"
+
+#include <map>
+#include <set>
+#include <sstream>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/format_macros.h>
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/cycle_breaker.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/payload_generator/graph_types.h"
+#include "update_engine/payload_generator/graph_utils.h"
+
+using std::map;
+using std::set;
+using std::string;
+using std::stringstream;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+using Block = InplaceGenerator::Block;
+
+namespace {
+
+void GenVertex(Vertex* out,
+               const vector<Extent>& src_extents,
+               const vector<Extent>& dst_extents,
+               const string& path,
+               InstallOperation_Type type) {
+  out->aop.op.set_type(type);
+  out->aop.name = path;
+  StoreExtents(src_extents, out->aop.op.mutable_src_extents());
+  StoreExtents(dst_extents, out->aop.op.mutable_dst_extents());
+}
+
+vector<Extent> VectOfExt(uint64_t start_block, uint64_t num_blocks) {
+  return vector<Extent>(1, ExtentForRange(start_block, num_blocks));
+}
+
+EdgeProperties EdgeWithReadDep(const vector<Extent>& extents) {
+  EdgeProperties ret;
+  ret.extents = extents;
+  return ret;
+}
+
+EdgeProperties EdgeWithWriteDep(const vector<Extent>& extents) {
+  EdgeProperties ret;
+  ret.write_extents = extents;
+  return ret;
+}
+
+template<typename T>
+void DumpVect(const vector<T>& vect) {
+  stringstream ss(stringstream::out);
+  for (typename vector<T>::const_iterator it = vect.begin(), e = vect.end();
+       it != e; ++it) {
+    ss << *it << ", ";
+  }
+  LOG(INFO) << "{" << ss.str() << "}";
+}
+
+void AppendExtent(vector<Extent>* vect, uint64_t start, uint64_t length) {
+  vect->resize(vect->size() + 1);
+  vect->back().set_start_block(start);
+  vect->back().set_num_blocks(length);
+}
+
+void OpAppendExtent(InstallOperation* op, uint64_t start, uint64_t length) {
+  Extent* extent = op->add_src_extents();
+  extent->set_start_block(start);
+  extent->set_num_blocks(length);
+}
+
+}  // namespace
+
+class InplaceGeneratorTest : public ::testing::Test {
+ protected:
+  // Initialize |blob_path_|, |blob_file_size_| and |blob_file_fd_| variables
+  // with a new blob file. The file is closed and removed automatically when
+  // the test finishes.
+  void CreateBlobFile() {
+    // blob_fd_closer_ takes a pointer to blob_fd_. Make sure we destroy a
+    // previous instance before overriding blob_fd_.
+    blob_fd_closer_.reset();
+    EXPECT_TRUE(utils::MakeTempFile(
+        "InplaceGenerator_blob_file.XXXXXX", &blob_path_, &blob_fd_));
+    blob_path_unlinker_.reset(new ScopedPathUnlinker(blob_path_));
+    blob_fd_closer_.reset(new ScopedFdCloser(&blob_fd_));
+    blob_file_size_ = 0;
+    EXPECT_GE(blob_fd_, 0);
+    blob_file_.reset(new BlobFileWriter(blob_fd_, &blob_file_size_));
+  }
+
+  // Blob file name, file descriptor and file size used to store operation
+  // blobs.
+  string blob_path_;
+  int blob_fd_{-1};
+  off_t blob_file_size_{0};
+  std::unique_ptr<BlobFileWriter> blob_file_;
+  std::unique_ptr<ScopedPathUnlinker> blob_path_unlinker_;
+  std::unique_ptr<ScopedFdCloser> blob_fd_closer_;
+};
+
+TEST_F(InplaceGeneratorTest, BlockDefaultValues) {
+  // Tests that a Block is initialized with the default values as a
+  // Vertex::kInvalidIndex. This is required by the delta generators.
+  Block block;
+  EXPECT_EQ(Vertex::kInvalidIndex, block.reader);
+  EXPECT_EQ(Vertex::kInvalidIndex, block.writer);
+}
+
+TEST_F(InplaceGeneratorTest, SubstituteBlocksTest) {
+  vector<Extent> remove_blocks;
+  AppendExtent(&remove_blocks, 3, 3);
+  AppendExtent(&remove_blocks, 7, 1);
+  vector<Extent> replace_blocks;
+  AppendExtent(&replace_blocks, 10, 2);
+  AppendExtent(&replace_blocks, 13, 2);
+  Vertex vertex;
+  InstallOperation& op = vertex.aop.op;
+  OpAppendExtent(&op, 4, 3);
+  OpAppendExtent(&op, kSparseHole, 4);  // Sparse hole in file
+  OpAppendExtent(&op, 3, 1);
+  OpAppendExtent(&op, 7, 3);
+
+  InplaceGenerator::SubstituteBlocks(&vertex, remove_blocks, replace_blocks);
+
+  EXPECT_EQ(7, op.src_extents_size());
+  EXPECT_EQ(11, op.src_extents(0).start_block());
+  EXPECT_EQ(1, op.src_extents(0).num_blocks());
+  EXPECT_EQ(13, op.src_extents(1).start_block());
+  EXPECT_EQ(1, op.src_extents(1).num_blocks());
+  EXPECT_EQ(6, op.src_extents(2).start_block());
+  EXPECT_EQ(1, op.src_extents(2).num_blocks());
+  EXPECT_EQ(kSparseHole, op.src_extents(3).start_block());
+  EXPECT_EQ(4, op.src_extents(3).num_blocks());
+  EXPECT_EQ(10, op.src_extents(4).start_block());
+  EXPECT_EQ(1, op.src_extents(4).num_blocks());
+  EXPECT_EQ(14, op.src_extents(5).start_block());
+  EXPECT_EQ(1, op.src_extents(5).num_blocks());
+  EXPECT_EQ(8, op.src_extents(6).start_block());
+  EXPECT_EQ(2, op.src_extents(6).num_blocks());
+}
+
+TEST_F(InplaceGeneratorTest, CutEdgesTest) {
+  Graph graph;
+  vector<Block> blocks(9);
+
+  // Create nodes in graph
+  {
+    graph.resize(graph.size() + 1);
+    graph.back().aop.op.set_type(InstallOperation::MOVE);
+    // Reads from blocks 3, 5, 7
+    vector<Extent> extents;
+    AppendBlockToExtents(&extents, 3);
+    AppendBlockToExtents(&extents, 5);
+    AppendBlockToExtents(&extents, 7);
+    StoreExtents(extents, graph.back().aop.op.mutable_src_extents());
+    blocks[3].reader = graph.size() - 1;
+    blocks[5].reader = graph.size() - 1;
+    blocks[7].reader = graph.size() - 1;
+
+    // Writes to blocks 1, 2, 4
+    extents.clear();
+    AppendBlockToExtents(&extents, 1);
+    AppendBlockToExtents(&extents, 2);
+    AppendBlockToExtents(&extents, 4);
+    StoreExtents(extents, graph.back().aop.op.mutable_dst_extents());
+    blocks[1].writer = graph.size() - 1;
+    blocks[2].writer = graph.size() - 1;
+    blocks[4].writer = graph.size() - 1;
+  }
+  {
+    graph.resize(graph.size() + 1);
+    graph.back().aop.op.set_type(InstallOperation::MOVE);
+    // Reads from blocks 1, 2, 4
+    vector<Extent> extents;
+    AppendBlockToExtents(&extents, 1);
+    AppendBlockToExtents(&extents, 2);
+    AppendBlockToExtents(&extents, 4);
+    StoreExtents(extents, graph.back().aop.op.mutable_src_extents());
+    blocks[1].reader = graph.size() - 1;
+    blocks[2].reader = graph.size() - 1;
+    blocks[4].reader = graph.size() - 1;
+
+    // Writes to blocks 3, 5, 6
+    extents.clear();
+    AppendBlockToExtents(&extents, 3);
+    AppendBlockToExtents(&extents, 5);
+    AppendBlockToExtents(&extents, 6);
+    StoreExtents(extents, graph.back().aop.op.mutable_dst_extents());
+    blocks[3].writer = graph.size() - 1;
+    blocks[5].writer = graph.size() - 1;
+    blocks[6].writer = graph.size() - 1;
+  }
+
+  // Create edges
+  InplaceGenerator::CreateEdges(&graph, blocks);
+
+  // Find cycles
+  CycleBreaker cycle_breaker;
+  set<Edge> cut_edges;
+  cycle_breaker.BreakCycles(graph, &cut_edges);
+
+  EXPECT_EQ(1, cut_edges.size());
+  EXPECT_TRUE(cut_edges.end() != cut_edges.find(
+      std::pair<Vertex::Index, Vertex::Index>(1, 0)));
+
+  vector<CutEdgeVertexes> cuts;
+  EXPECT_TRUE(InplaceGenerator::CutEdges(&graph, cut_edges, &cuts));
+
+  EXPECT_EQ(3, graph.size());
+
+  // Check new node in graph:
+  EXPECT_EQ(InstallOperation::MOVE, graph.back().aop.op.type());
+  EXPECT_EQ(2, graph.back().aop.op.src_extents_size());
+  EXPECT_EQ(1, graph.back().aop.op.dst_extents_size());
+  EXPECT_EQ(kTempBlockStart, graph.back().aop.op.dst_extents(0).start_block());
+  EXPECT_EQ(2, graph.back().aop.op.dst_extents(0).num_blocks());
+  EXPECT_TRUE(graph.back().out_edges.empty());
+
+  // Check that old node reads from new blocks
+  EXPECT_EQ(2, graph[0].aop.op.src_extents_size());
+  EXPECT_EQ(kTempBlockStart, graph[0].aop.op.src_extents(0).start_block());
+  EXPECT_EQ(2, graph[0].aop.op.src_extents(0).num_blocks());
+  EXPECT_EQ(7, graph[0].aop.op.src_extents(1).start_block());
+  EXPECT_EQ(1, graph[0].aop.op.src_extents(1).num_blocks());
+
+  // And that the old dst extents haven't changed
+  EXPECT_EQ(2, graph[0].aop.op.dst_extents_size());
+  EXPECT_EQ(1, graph[0].aop.op.dst_extents(0).start_block());
+  EXPECT_EQ(2, graph[0].aop.op.dst_extents(0).num_blocks());
+  EXPECT_EQ(4, graph[0].aop.op.dst_extents(1).start_block());
+  EXPECT_EQ(1, graph[0].aop.op.dst_extents(1).num_blocks());
+
+  // Ensure it only depends on the next node and the new temp node
+  EXPECT_EQ(2, graph[0].out_edges.size());
+  EXPECT_TRUE(graph[0].out_edges.end() != graph[0].out_edges.find(1));
+  EXPECT_TRUE(graph[0].out_edges.end() != graph[0].out_edges.find(graph.size() -
+                                                                  1));
+
+  // Check second node has unchanged extents
+  EXPECT_EQ(2, graph[1].aop.op.src_extents_size());
+  EXPECT_EQ(1, graph[1].aop.op.src_extents(0).start_block());
+  EXPECT_EQ(2, graph[1].aop.op.src_extents(0).num_blocks());
+  EXPECT_EQ(4, graph[1].aop.op.src_extents(1).start_block());
+  EXPECT_EQ(1, graph[1].aop.op.src_extents(1).num_blocks());
+
+  EXPECT_EQ(2, graph[1].aop.op.dst_extents_size());
+  EXPECT_EQ(3, graph[1].aop.op.dst_extents(0).start_block());
+  EXPECT_EQ(1, graph[1].aop.op.dst_extents(0).num_blocks());
+  EXPECT_EQ(5, graph[1].aop.op.dst_extents(1).start_block());
+  EXPECT_EQ(2, graph[1].aop.op.dst_extents(1).num_blocks());
+
+  // Ensure it only depends on the next node
+  EXPECT_EQ(1, graph[1].out_edges.size());
+  EXPECT_TRUE(graph[1].out_edges.end() != graph[1].out_edges.find(2));
+}
+
+TEST_F(InplaceGeneratorTest, AssignTempBlocksReuseTest) {
+  Graph graph(9);
+
+  const vector<Extent> empt;
+  uint64_t tmp = kTempBlockStart;
+  const string kFilename = "/foo";
+
+  vector<CutEdgeVertexes> cuts;
+  cuts.resize(3);
+
+  // Simple broken loop:
+  GenVertex(
+      &graph[0], VectOfExt(0, 1), VectOfExt(1, 1), "", InstallOperation::MOVE);
+  GenVertex(&graph[1],
+            VectOfExt(tmp, 1),
+            VectOfExt(0, 1),
+            "",
+            InstallOperation::MOVE);
+  GenVertex(&graph[2],
+            VectOfExt(1, 1),
+            VectOfExt(tmp, 1),
+            "",
+            InstallOperation::MOVE);
+  // Corresponding edges:
+  graph[0].out_edges[2] = EdgeWithReadDep(VectOfExt(1, 1));
+  graph[1].out_edges[2] = EdgeWithWriteDep(VectOfExt(tmp, 1));
+  graph[1].out_edges[0] = EdgeWithReadDep(VectOfExt(0, 1));
+  // Store the cut:
+  cuts[0].old_dst = 1;
+  cuts[0].old_src = 0;
+  cuts[0].new_vertex = 2;
+  cuts[0].tmp_extents = VectOfExt(tmp, 1);
+  tmp++;
+
+  // Slightly more complex pair of loops:
+  GenVertex(
+      &graph[3], VectOfExt(4, 2), VectOfExt(2, 2), "", InstallOperation::MOVE);
+  GenVertex(
+      &graph[4], VectOfExt(6, 1), VectOfExt(7, 1), "", InstallOperation::MOVE);
+  GenVertex(&graph[5],
+            VectOfExt(tmp, 3),
+            VectOfExt(4, 3),
+            kFilename,
+            InstallOperation::MOVE);
+  GenVertex(&graph[6],
+            VectOfExt(2, 2),
+            VectOfExt(tmp, 2),
+            "",
+            InstallOperation::MOVE);
+  GenVertex(&graph[7],
+            VectOfExt(7, 1),
+            VectOfExt(tmp + 2, 1),
+            "",
+            InstallOperation::MOVE);
+  // Corresponding edges:
+  graph[3].out_edges[6] = EdgeWithReadDep(VectOfExt(2, 2));
+  graph[4].out_edges[7] = EdgeWithReadDep(VectOfExt(7, 1));
+  graph[5].out_edges[6] = EdgeWithWriteDep(VectOfExt(tmp, 2));
+  graph[5].out_edges[7] = EdgeWithWriteDep(VectOfExt(tmp + 2, 1));
+  graph[5].out_edges[3] = EdgeWithReadDep(VectOfExt(4, 2));
+  graph[5].out_edges[4] = EdgeWithReadDep(VectOfExt(6, 1));
+  // Store the cuts:
+  cuts[1].old_dst = 5;
+  cuts[1].old_src = 3;
+  cuts[1].new_vertex = 6;
+  cuts[1].tmp_extents = VectOfExt(tmp, 2);
+  cuts[2].old_dst = 5;
+  cuts[2].old_src = 4;
+  cuts[2].new_vertex = 7;
+  cuts[2].tmp_extents = VectOfExt(tmp + 2, 1);
+
+  // Supplier of temp block:
+  GenVertex(&graph[8], empt, VectOfExt(8, 1), "", InstallOperation::REPLACE);
+
+  // Specify the final order:
+  vector<Vertex::Index> op_indexes;
+  op_indexes.push_back(2);
+  op_indexes.push_back(0);
+  op_indexes.push_back(1);
+  op_indexes.push_back(6);
+  op_indexes.push_back(3);
+  op_indexes.push_back(7);
+  op_indexes.push_back(4);
+  op_indexes.push_back(5);
+  op_indexes.push_back(8);
+
+  vector<vector<Vertex::Index>::size_type> reverse_op_indexes;
+  InplaceGenerator::GenerateReverseTopoOrderMap(op_indexes,
+                                                &reverse_op_indexes);
+
+  CreateBlobFile();
+  EXPECT_TRUE(InplaceGenerator::AssignTempBlocks(&graph,
+                                                 "/dev/zero",
+                                                 blob_file_.get(),
+                                                 &op_indexes,
+                                                 &reverse_op_indexes,
+                                                 cuts));
+  EXPECT_FALSE(graph[6].valid);
+  EXPECT_FALSE(graph[7].valid);
+  EXPECT_EQ(1, graph[1].aop.op.src_extents_size());
+  EXPECT_EQ(2, graph[1].aop.op.src_extents(0).start_block());
+  EXPECT_EQ(1, graph[1].aop.op.src_extents(0).num_blocks());
+  EXPECT_EQ(InstallOperation::REPLACE_BZ, graph[5].aop.op.type());
+}
+
+TEST_F(InplaceGeneratorTest, MoveAndSortFullOpsToBackTest) {
+  Graph graph(4);
+  graph[0].aop.name = "A";
+  graph[0].aop.op.set_type(InstallOperation::REPLACE);
+  graph[1].aop.name = "B";
+  graph[1].aop.op.set_type(InstallOperation::BSDIFF);
+  graph[2].aop.name = "C";
+  graph[2].aop.op.set_type(InstallOperation::REPLACE_BZ);
+  graph[3].aop.name = "D";
+  graph[3].aop.op.set_type(InstallOperation::MOVE);
+
+  vector<Vertex::Index> vect(graph.size());
+
+  for (vector<Vertex::Index>::size_type i = 0; i < vect.size(); ++i) {
+    vect[i] = i;
+  }
+  InplaceGenerator::MoveAndSortFullOpsToBack(&graph, &vect);
+  EXPECT_EQ(vect.size(), graph.size());
+  EXPECT_EQ(graph[vect[0]].aop.name, "B");
+  EXPECT_EQ(graph[vect[1]].aop.name, "D");
+  EXPECT_EQ(graph[vect[2]].aop.name, "A");
+  EXPECT_EQ(graph[vect[3]].aop.name, "C");
+}
+
+TEST_F(InplaceGeneratorTest, AssignTempBlocksTest) {
+  Graph graph(9);
+  const vector<Extent> empt;  // empty
+  const string kFilename = "/foo";
+
+  // Some scratch space:
+  GenVertex(&graph[0], empt, VectOfExt(200, 1), "", InstallOperation::REPLACE);
+  GenVertex(&graph[1], empt, VectOfExt(210, 10), "", InstallOperation::REPLACE);
+  GenVertex(&graph[2], empt, VectOfExt(220, 1), "", InstallOperation::REPLACE);
+
+  // A cycle that requires 10 blocks to break:
+  GenVertex(&graph[3],
+            VectOfExt(10, 11),
+            VectOfExt(0, 9),
+            "",
+            InstallOperation::BSDIFF);
+  graph[3].out_edges[4] = EdgeWithReadDep(VectOfExt(0, 9));
+  GenVertex(&graph[4],
+            VectOfExt(0, 9),
+            VectOfExt(10, 11),
+            "",
+            InstallOperation::BSDIFF);
+  graph[4].out_edges[3] = EdgeWithReadDep(VectOfExt(10, 11));
+
+  // A cycle that requires 9 blocks to break:
+  GenVertex(&graph[5],
+            VectOfExt(40, 11),
+            VectOfExt(30, 10),
+            "",
+            InstallOperation::BSDIFF);
+  graph[5].out_edges[6] = EdgeWithReadDep(VectOfExt(30, 10));
+  GenVertex(&graph[6],
+            VectOfExt(30, 10),
+            VectOfExt(40, 11),
+            "",
+            InstallOperation::BSDIFF);
+  graph[6].out_edges[5] = EdgeWithReadDep(VectOfExt(40, 11));
+
+  // A cycle that requires 40 blocks to break (which is too many):
+  GenVertex(&graph[7],
+            VectOfExt(120, 50),
+            VectOfExt(60, 40),
+            "",
+            InstallOperation::BSDIFF);
+  graph[7].out_edges[8] = EdgeWithReadDep(VectOfExt(60, 40));
+  GenVertex(&graph[8],
+            VectOfExt(60, 40),
+            VectOfExt(120, 50),
+            kFilename,
+            InstallOperation::BSDIFF);
+  graph[8].out_edges[7] = EdgeWithReadDep(VectOfExt(120, 50));
+
+  graph_utils::DumpGraph(graph);
+
+  vector<Vertex::Index> final_order;
+
+  CreateBlobFile();
+  EXPECT_TRUE(InplaceGenerator::ConvertGraphToDag(&graph,
+                                                  "/dev/zero",
+                                                  blob_file_.get(),
+                                                  &final_order,
+                                                  Vertex::kInvalidIndex));
+
+  Graph expected_graph(12);
+  GenVertex(&expected_graph[0],
+            empt,
+            VectOfExt(200, 1),
+            "",
+            InstallOperation::REPLACE);
+  GenVertex(&expected_graph[1],
+            empt,
+            VectOfExt(210, 10),
+            "",
+            InstallOperation::REPLACE);
+  GenVertex(&expected_graph[2],
+            empt,
+            VectOfExt(220, 1),
+            "",
+            InstallOperation::REPLACE);
+  GenVertex(&expected_graph[3],
+            VectOfExt(10, 11),
+            VectOfExt(0, 9),
+            "",
+            InstallOperation::BSDIFF);
+  expected_graph[3].out_edges[9] = EdgeWithReadDep(VectOfExt(0, 9));
+  GenVertex(&expected_graph[4],
+            VectOfExt(60, 9),
+            VectOfExt(10, 11),
+            "",
+            InstallOperation::BSDIFF);
+  expected_graph[4].out_edges[3] = EdgeWithReadDep(VectOfExt(10, 11));
+  expected_graph[4].out_edges[9] = EdgeWithWriteDep(VectOfExt(60, 9));
+  GenVertex(&expected_graph[5],
+            VectOfExt(40, 11),
+            VectOfExt(30, 10),
+            "",
+            InstallOperation::BSDIFF);
+  expected_graph[5].out_edges[10] = EdgeWithReadDep(VectOfExt(30, 10));
+
+  GenVertex(&expected_graph[6],
+            VectOfExt(60, 10),
+            VectOfExt(40, 11),
+            "",
+            InstallOperation::BSDIFF);
+  expected_graph[6].out_edges[5] = EdgeWithReadDep(VectOfExt(40, 11));
+  expected_graph[6].out_edges[10] = EdgeWithWriteDep(VectOfExt(60, 10));
+
+  GenVertex(&expected_graph[7],
+            VectOfExt(120, 50),
+            VectOfExt(60, 40),
+            "",
+            InstallOperation::BSDIFF);
+  expected_graph[7].out_edges[6] = EdgeWithReadDep(VectOfExt(60, 10));
+
+  GenVertex(&expected_graph[8],
+            empt,
+            VectOfExt(0, 50),
+            "/foo",
+            InstallOperation::REPLACE_BZ);
+  expected_graph[8].out_edges[7] = EdgeWithReadDep(VectOfExt(120, 50));
+
+  GenVertex(&expected_graph[9],
+            VectOfExt(0, 9),
+            VectOfExt(60, 9),
+            "",
+            InstallOperation::MOVE);
+
+  GenVertex(&expected_graph[10],
+            VectOfExt(30, 10),
+            VectOfExt(60, 10),
+            "",
+            InstallOperation::MOVE);
+  expected_graph[10].out_edges[4] = EdgeWithReadDep(VectOfExt(60, 9));
+
+  EXPECT_EQ(12, graph.size());
+  EXPECT_FALSE(graph.back().valid);
+  for (Graph::size_type i = 0; i < graph.size() - 1; i++) {
+    EXPECT_TRUE(graph[i].out_edges == expected_graph[i].out_edges);
+    if (i == 8) {
+      // special case
+    } else {
+      // EXPECT_TRUE(graph[i] == expected_graph[i]) << "i = " << i;
+    }
+  }
+}
+
+TEST_F(InplaceGeneratorTest, CreateScratchNodeTest) {
+  Vertex vertex;
+  InplaceGenerator::CreateScratchNode(12, 34, &vertex);
+  EXPECT_EQ(InstallOperation::REPLACE_BZ, vertex.aop.op.type());
+  EXPECT_EQ(0, vertex.aop.op.data_offset());
+  EXPECT_EQ(0, vertex.aop.op.data_length());
+  EXPECT_EQ(1, vertex.aop.op.dst_extents_size());
+  EXPECT_EQ(12, vertex.aop.op.dst_extents(0).start_block());
+  EXPECT_EQ(34, vertex.aop.op.dst_extents(0).num_blocks());
+}
+
+TEST_F(InplaceGeneratorTest, ApplyMapTest) {
+  vector<uint64_t> collection = {1, 2, 3, 4, 6};
+  vector<uint64_t> expected_values = {1, 2, 5, 4, 8};
+  map<uint64_t, uint64_t> value_map;
+  value_map[3] = 5;
+  value_map[6] = 8;
+  value_map[5] = 10;
+
+  InplaceGenerator::ApplyMap(&collection, value_map);
+  EXPECT_EQ(expected_values, collection);
+}
+
+// We can't produce MOVE operations with a source or destination in the block 0.
+// This test checks that the cycle breaker procedure doesn't produce such
+// operations.
+TEST_F(InplaceGeneratorTest, ResolveReadAfterWriteDependenciesAvoidMoveToZero) {
+  size_t block_size = 4096;
+  size_t num_blocks = 4;
+  vector<AnnotatedOperation> aops;
+
+  // Create a REPLACE_BZ for block 0, and a circular dependency among all other
+  // blocks. This situation would prefer to issue a MOVE to scratch space and
+  // the only available block is 0.
+  aops.emplace_back();
+  aops.back().name = base::StringPrintf("<bz-block-0>");
+  aops.back().op.set_type(InstallOperation::REPLACE_BZ);
+  StoreExtents({ExtentForRange(0, 1)}, aops.back().op.mutable_dst_extents());
+
+  for (size_t i = 1; i < num_blocks; i++) {
+    AnnotatedOperation aop;
+    aop.name = base::StringPrintf("<op-%" PRIuS ">", i);
+    aop.op.set_type(InstallOperation::BSDIFF);
+    StoreExtents({ExtentForRange(1 + i % (num_blocks - 1), 1)},
+                 aop.op.mutable_src_extents());
+    StoreExtents({ExtentForRange(i, 1)}, aop.op.mutable_dst_extents());
+    aops.push_back(aop);
+  }
+
+  PartitionConfig part("part");
+  part.path = "/dev/zero";
+  part.size = num_blocks * block_size;
+
+  CreateBlobFile();
+
+  // We ran two tests here. The first one without enough blocks for the scratch
+  // space, forcing it to create a new full operation and the second case with
+  // one extra block in the partition that can be used for the move operation.
+  for (const auto part_blocks : vector<uint64_t>{num_blocks, num_blocks + 1}) {
+    SCOPED_TRACE(base::StringPrintf("Using partition_blocs=%" PRIu64,
+                                    part_blocks));
+    vector<AnnotatedOperation> result_aops = aops;
+    EXPECT_TRUE(InplaceGenerator::ResolveReadAfterWriteDependencies(
+      part, part_blocks * block_size, block_size, blob_file_.get(),
+      &result_aops));
+
+    size_t full_ops = 0;
+    for (const auto& aop : result_aops) {
+      if (aop.op.type() == InstallOperation::REPLACE ||
+          aop.op.type() == InstallOperation::REPLACE_BZ) {
+        full_ops++;
+      }
+
+      if (aop.op.type() != InstallOperation::MOVE)
+        continue;
+      for (const Extent& extent : aop.op.src_extents()) {
+        EXPECT_NE(0, extent.start_block()) << "On src extents for aop: " << aop;
+      }
+      for (const Extent& extent : aop.op.dst_extents()) {
+        EXPECT_NE(0, extent.start_block()) << "On dst extents for aop: " << aop;
+      }
+    }
+
+    // If there's extra space in the partition, it should not use a new full
+    // operation for it.
+    EXPECT_EQ(part_blocks == num_blocks ? 2 : 1, full_ops);
+
+    if (HasNonfatalFailure()) {
+      LOG(INFO) << "Result operation list:";
+      for (const auto& aop : result_aops) {
+        LOG(INFO) << aop;
+      }
+    }
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/operations_generator.h b/payload_generator/operations_generator.h
new file mode 100644
index 0000000..9127d7b
--- /dev/null
+++ b/payload_generator/operations_generator.h
@@ -0,0 +1,59 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_OPERATIONS_GENERATOR_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_OPERATIONS_GENERATOR_H_
+
+#include <vector>
+
+#include <base/macros.h>
+
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/blob_file_writer.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+
+namespace chromeos_update_engine {
+
+class OperationsGenerator {
+ public:
+  virtual ~OperationsGenerator() = default;
+
+  // This method generates a list of operations to update from the partition
+  // |old_part| to |new_part| and stores the generated operations in |aops|.
+  // These operations are generated based on the given |config|.
+  // The operations should be applied in the order specified in the list, and
+  // they respect the payload version and type (delta or full) specified in
+  // |config|.
+  // The operations generated will refer to offsets in the file |blob_file|,
+  // where this function stores the output, but not necessarily in the same
+  // order as they appear in the |aops|.
+  virtual bool GenerateOperations(
+      const PayloadGenerationConfig& config,
+      const PartitionConfig& old_part,
+      const PartitionConfig& new_part,
+      BlobFileWriter* blob_file,
+      std::vector<AnnotatedOperation>* aops) = 0;
+
+ protected:
+  OperationsGenerator() = default;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(OperationsGenerator);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_OPERATIONS_GENERATOR_H_
diff --git a/payload_generator/payload_file.cc b/payload_generator/payload_file.cc
new file mode 100644
index 0000000..d268ab8
--- /dev/null
+++ b/payload_generator/payload_file.cc
@@ -0,0 +1,356 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/payload_file.h"
+
+#include <endian.h>
+
+#include <algorithm>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/file_writer.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/delta_diff_utils.h"
+#include "update_engine/payload_generator/payload_signer.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+struct DeltaObject {
+  DeltaObject(const string& in_name, const int in_type, const off_t in_size)
+      : name(in_name),
+        type(in_type),
+        size(in_size) {}
+  bool operator <(const DeltaObject& object) const {
+    return (size != object.size) ? (size < object.size) : (name < object.name);
+  }
+  string name;
+  int type;
+  off_t size;
+};
+
+// Writes the uint64_t passed in in host-endian to the file as big-endian.
+// Returns true on success.
+bool WriteUint64AsBigEndian(FileWriter* writer, const uint64_t value) {
+  uint64_t value_be = htobe64(value);
+  TEST_AND_RETURN_FALSE(writer->Write(&value_be, sizeof(value_be)));
+  return true;
+}
+
+}  // namespace
+
+bool PayloadFile::Init(const PayloadGenerationConfig& config) {
+  major_version_ = config.major_version;
+  TEST_AND_RETURN_FALSE(major_version_ == kChromeOSMajorPayloadVersion ||
+                        major_version_ == kBrilloMajorPayloadVersion);
+  manifest_.set_minor_version(config.minor_version);
+
+  if (!config.source.ImageInfoIsEmpty())
+    *(manifest_.mutable_old_image_info()) = config.source.image_info;
+
+  if (!config.target.ImageInfoIsEmpty())
+    *(manifest_.mutable_new_image_info()) = config.target.image_info;
+
+  manifest_.set_block_size(config.block_size);
+  return true;
+}
+
+bool PayloadFile::AddPartition(const PartitionConfig& old_conf,
+                               const PartitionConfig& new_conf,
+                               const vector<AnnotatedOperation>& aops) {
+  // Check partitions order for Chrome OS
+  if (major_version_ == kChromeOSMajorPayloadVersion) {
+    const vector<const char*> part_order = { kLegacyPartitionNameRoot,
+                                             kLegacyPartitionNameKernel };
+    TEST_AND_RETURN_FALSE(part_vec_.size() < part_order.size());
+    TEST_AND_RETURN_FALSE(new_conf.name == part_order[part_vec_.size()]);
+  }
+  Partition part;
+  part.name = new_conf.name;
+  part.aops = aops;
+  part.postinstall = new_conf.postinstall;
+  // Initialize the PartitionInfo objects if present.
+  if (!old_conf.path.empty())
+    TEST_AND_RETURN_FALSE(diff_utils::InitializePartitionInfo(old_conf,
+                                                              &part.old_info));
+  TEST_AND_RETURN_FALSE(diff_utils::InitializePartitionInfo(new_conf,
+                                                            &part.new_info));
+  part_vec_.push_back(std::move(part));
+  return true;
+}
+
+bool PayloadFile::WritePayload(const string& payload_file,
+                               const string& data_blobs_path,
+                               const string& private_key_path,
+                               uint64_t* metadata_size_out) {
+  // Reorder the data blobs with the manifest_.
+  string ordered_blobs_path;
+  TEST_AND_RETURN_FALSE(utils::MakeTempFile(
+      "CrAU_temp_data.ordered.XXXXXX",
+      &ordered_blobs_path,
+      nullptr));
+  ScopedPathUnlinker ordered_blobs_unlinker(ordered_blobs_path);
+  TEST_AND_RETURN_FALSE(ReorderDataBlobs(data_blobs_path, ordered_blobs_path));
+
+  // Check that install op blobs are in order.
+  uint64_t next_blob_offset = 0;
+  for (const auto& part : part_vec_) {
+    for (const auto& aop : part.aops) {
+      if (!aop.op.has_data_offset())
+        continue;
+      if (aop.op.data_offset() != next_blob_offset) {
+        LOG(FATAL) << "bad blob offset! " << aop.op.data_offset() << " != "
+                   << next_blob_offset;
+      }
+      next_blob_offset += aop.op.data_length();
+    }
+  }
+
+  // Copy the operations and partition info from the part_vec_ to the manifest.
+  manifest_.clear_install_operations();
+  manifest_.clear_kernel_install_operations();
+  manifest_.clear_partitions();
+  for (const auto& part : part_vec_) {
+    if (major_version_ == kBrilloMajorPayloadVersion) {
+      PartitionUpdate* partition = manifest_.add_partitions();
+      partition->set_partition_name(part.name);
+      if (part.postinstall.run) {
+        partition->set_run_postinstall(true);
+        if (!part.postinstall.path.empty())
+          partition->set_postinstall_path(part.postinstall.path);
+        if (!part.postinstall.filesystem_type.empty())
+          partition->set_filesystem_type(part.postinstall.filesystem_type);
+      }
+      for (const AnnotatedOperation& aop : part.aops) {
+        *partition->add_operations() = aop.op;
+      }
+      if (part.old_info.has_size() || part.old_info.has_hash())
+        *(partition->mutable_old_partition_info()) = part.old_info;
+      if (part.new_info.has_size() || part.new_info.has_hash())
+        *(partition->mutable_new_partition_info()) = part.new_info;
+    } else {
+      // major_version_ == kChromeOSMajorPayloadVersion
+      if (part.name == kLegacyPartitionNameKernel) {
+        for (const AnnotatedOperation& aop : part.aops)
+          *manifest_.add_kernel_install_operations() = aop.op;
+        if (part.old_info.has_size() || part.old_info.has_hash())
+          *manifest_.mutable_old_kernel_info() = part.old_info;
+        if (part.new_info.has_size() || part.new_info.has_hash())
+          *manifest_.mutable_new_kernel_info() = part.new_info;
+      } else {
+        for (const AnnotatedOperation& aop : part.aops)
+          *manifest_.add_install_operations() = aop.op;
+        if (part.old_info.has_size() || part.old_info.has_hash())
+          *manifest_.mutable_old_rootfs_info() = part.old_info;
+        if (part.new_info.has_size() || part.new_info.has_hash())
+          *manifest_.mutable_new_rootfs_info() = part.new_info;
+      }
+    }
+  }
+
+  // Signatures appear at the end of the blobs. Note the offset in the
+  // manifest_.
+  uint64_t signature_blob_length = 0;
+  if (!private_key_path.empty()) {
+    TEST_AND_RETURN_FALSE(
+        PayloadSigner::SignatureBlobLength(vector<string>(1, private_key_path),
+                                           &signature_blob_length));
+    PayloadSigner::AddSignatureToManifest(
+        next_blob_offset, signature_blob_length,
+        major_version_ == kChromeOSMajorPayloadVersion, &manifest_);
+  }
+
+  // Serialize protobuf
+  string serialized_manifest;
+  TEST_AND_RETURN_FALSE(manifest_.AppendToString(&serialized_manifest));
+
+  uint64_t metadata_size =
+      sizeof(kDeltaMagic) + 2 * sizeof(uint64_t) + serialized_manifest.size();
+
+  LOG(INFO) << "Writing final delta file header...";
+  DirectFileWriter writer;
+  TEST_AND_RETURN_FALSE_ERRNO(writer.Open(payload_file.c_str(),
+                                          O_WRONLY | O_CREAT | O_TRUNC,
+                                          0644) == 0);
+  ScopedFileWriterCloser writer_closer(&writer);
+
+  // Write header
+  TEST_AND_RETURN_FALSE(writer.Write(kDeltaMagic, sizeof(kDeltaMagic)));
+
+  // Write major version number
+  TEST_AND_RETURN_FALSE(WriteUint64AsBigEndian(&writer, major_version_));
+
+  // Write protobuf length
+  TEST_AND_RETURN_FALSE(WriteUint64AsBigEndian(&writer,
+                                               serialized_manifest.size()));
+
+  // Write metadata signature size.
+  uint32_t metadata_signature_size = 0;
+  if (major_version_ == kBrilloMajorPayloadVersion) {
+    // Metadata signature has the same size as payload signature, because they
+    // are both the same kind of signature for the same kind of hash.
+    uint32_t metadata_signature_size = htobe32(signature_blob_length);
+    TEST_AND_RETURN_FALSE(writer.Write(&metadata_signature_size,
+                                       sizeof(metadata_signature_size)));
+    metadata_size += sizeof(metadata_signature_size);
+    // Set correct size instead of big endian size.
+    metadata_signature_size = signature_blob_length;
+  }
+
+  // Write protobuf
+  LOG(INFO) << "Writing final delta file protobuf... "
+            << serialized_manifest.size();
+  TEST_AND_RETURN_FALSE(writer.Write(serialized_manifest.data(),
+                                     serialized_manifest.size()));
+
+  // Write metadata signature blob.
+  if (major_version_ == kBrilloMajorPayloadVersion &&
+      !private_key_path.empty()) {
+    brillo::Blob metadata_hash, metadata_signature;
+    TEST_AND_RETURN_FALSE(HashCalculator::RawHashOfFile(payload_file,
+                                                             metadata_size,
+                                                             &metadata_hash));
+    TEST_AND_RETURN_FALSE(
+        PayloadSigner::SignHashWithKeys(metadata_hash,
+                                        vector<string>(1, private_key_path),
+                                        &metadata_signature));
+    TEST_AND_RETURN_FALSE(writer.Write(metadata_signature.data(),
+                                       metadata_signature.size()));
+  }
+
+  // Append the data blobs
+  LOG(INFO) << "Writing final delta file data blobs...";
+  int blobs_fd = open(ordered_blobs_path.c_str(), O_RDONLY, 0);
+  ScopedFdCloser blobs_fd_closer(&blobs_fd);
+  TEST_AND_RETURN_FALSE(blobs_fd >= 0);
+  for (;;) {
+    vector<char> buf(1024 * 1024);
+    ssize_t rc = read(blobs_fd, buf.data(), buf.size());
+    if (0 == rc) {
+      // EOF
+      break;
+    }
+    TEST_AND_RETURN_FALSE_ERRNO(rc > 0);
+    TEST_AND_RETURN_FALSE(writer.Write(buf.data(), rc));
+  }
+
+  // Write payload signature blob.
+  if (!private_key_path.empty()) {
+    LOG(INFO) << "Signing the update...";
+    brillo::Blob signature_blob;
+    TEST_AND_RETURN_FALSE(PayloadSigner::SignPayload(
+        payload_file,
+        vector<string>(1, private_key_path),
+        metadata_size,
+        metadata_signature_size,
+        metadata_size + metadata_signature_size + manifest_.signatures_offset(),
+        &signature_blob));
+    TEST_AND_RETURN_FALSE(writer.Write(signature_blob.data(),
+                                       signature_blob.size()));
+  }
+
+  ReportPayloadUsage(metadata_size);
+  *metadata_size_out = metadata_size;
+  return true;
+}
+
+bool PayloadFile::ReorderDataBlobs(
+    const string& data_blobs_path,
+    const string& new_data_blobs_path) {
+  int in_fd = open(data_blobs_path.c_str(), O_RDONLY, 0);
+  TEST_AND_RETURN_FALSE_ERRNO(in_fd >= 0);
+  ScopedFdCloser in_fd_closer(&in_fd);
+
+  DirectFileWriter writer;
+  TEST_AND_RETURN_FALSE(
+      writer.Open(new_data_blobs_path.c_str(),
+                  O_WRONLY | O_TRUNC | O_CREAT,
+                  0644) == 0);
+  ScopedFileWriterCloser writer_closer(&writer);
+  uint64_t out_file_size = 0;
+
+  for (auto& part: part_vec_) {
+    for (AnnotatedOperation& aop : part.aops) {
+      if (!aop.op.has_data_offset())
+        continue;
+      CHECK(aop.op.has_data_length());
+      brillo::Blob buf(aop.op.data_length());
+      ssize_t rc = pread(in_fd, buf.data(), buf.size(), aop.op.data_offset());
+      TEST_AND_RETURN_FALSE(rc == static_cast<ssize_t>(buf.size()));
+
+      // Add the hash of the data blobs for this operation
+      TEST_AND_RETURN_FALSE(AddOperationHash(&aop.op, buf));
+
+      aop.op.set_data_offset(out_file_size);
+      TEST_AND_RETURN_FALSE(writer.Write(buf.data(), buf.size()));
+      out_file_size += buf.size();
+    }
+  }
+  return true;
+}
+
+bool PayloadFile::AddOperationHash(InstallOperation* op,
+                                   const brillo::Blob& buf) {
+  HashCalculator hasher;
+  TEST_AND_RETURN_FALSE(hasher.Update(buf.data(), buf.size()));
+  TEST_AND_RETURN_FALSE(hasher.Finalize());
+  const brillo::Blob& hash = hasher.raw_hash();
+  op->set_data_sha256_hash(hash.data(), hash.size());
+  return true;
+}
+
+void PayloadFile::ReportPayloadUsage(uint64_t metadata_size) const {
+  vector<DeltaObject> objects;
+  off_t total_size = 0;
+
+  for (const auto& part : part_vec_) {
+    for (const AnnotatedOperation& aop : part.aops) {
+      objects.push_back(DeltaObject(aop.name,
+                                    aop.op.type(),
+                                    aop.op.data_length()));
+      total_size += aop.op.data_length();
+    }
+  }
+
+  objects.push_back(DeltaObject("<manifest-metadata>",
+                                -1,
+                                metadata_size));
+  total_size += metadata_size;
+
+  std::sort(objects.begin(), objects.end());
+
+  static const char kFormatString[] = "%6.2f%% %10jd %-10s %s\n";
+  for (const DeltaObject& object : objects) {
+    fprintf(
+        stderr, kFormatString,
+        object.size * 100.0 / total_size,
+        static_cast<intmax_t>(object.size),
+        (object.type >= 0 ? InstallOperationTypeName(
+                                static_cast<InstallOperation_Type>(object.type))
+                          : "-"),
+        object.name.c_str());
+  }
+  fprintf(stderr, kFormatString,
+          100.0, static_cast<intmax_t>(total_size), "", "<total>");
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/payload_file.h b/payload_generator/payload_file.h
new file mode 100644
index 0000000..7cc792a
--- /dev/null
+++ b/payload_generator/payload_file.h
@@ -0,0 +1,105 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_FILE_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_FILE_H_
+
+#include <string>
+#include <vector>
+
+#include <brillo/secure_blob.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/payload_generator/annotated_operation.h"
+#include "update_engine/payload_generator/payload_generation_config.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+// Class to handle the creation of a payload file. This class is the only one
+// dealing with writing the payload and its format, but has no logic about what
+// should be on it.
+class PayloadFile {
+ public:
+  // Initialize the payload file with the payload generation config. It computes
+  // required hashes of the requested partitions.
+  bool Init(const PayloadGenerationConfig& config);
+
+  // Add a partition to the payload manifest. Including partition name, list of
+  // operations and partition info. The operations in |aops|
+  // reference a blob stored in the file provided to WritePayload().
+  bool AddPartition(const PartitionConfig& old_conf,
+                    const PartitionConfig& new_conf,
+                    const std::vector<AnnotatedOperation>& aops);
+
+  // Write the payload to the |payload_file| file. The operations reference
+  // blobs in the |data_blobs_path| file and the blobs will be reordered in the
+  // payload file to match the order of the operations. The size of the metadata
+  // section of the payload is stored in |metadata_size_out|.
+  bool WritePayload(const std::string& payload_file,
+                    const std::string& data_blobs_path,
+                    const std::string& private_key_path,
+                    uint64_t* metadata_size_out);
+
+ private:
+  FRIEND_TEST(PayloadFileTest, ReorderBlobsTest);
+
+  // Computes a SHA256 hash of the given buf and sets the hash value in the
+  // operation so that update_engine could verify. This hash should be set
+  // for all operations that have a non-zero data blob. One exception is the
+  // dummy operation for signature blob because the contents of the signature
+  // blob will not be available at payload creation time. So, update_engine will
+  // gracefully ignore the dummy signature operation.
+  static bool AddOperationHash(InstallOperation* op, const brillo::Blob& buf);
+
+  // Install operations in the manifest may reference data blobs, which
+  // are in data_blobs_path. This function creates a new data blobs file
+  // with the data blobs in the same order as the referencing install
+  // operations in the manifest. E.g. if manifest[0] has a data blob
+  // "X" at offset 1, manifest[1] has a data blob "Y" at offset 0,
+  // and data_blobs_path's file contains "YX", new_data_blobs_path
+  // will set to be a file that contains "XY".
+  bool ReorderDataBlobs(const std::string& data_blobs_path,
+                        const std::string& new_data_blobs_path);
+
+  // Print in stderr the Payload usage report.
+  void ReportPayloadUsage(uint64_t metadata_size) const;
+
+  // The major_version of the requested payload.
+  uint64_t major_version_;
+
+  DeltaArchiveManifest manifest_;
+
+  // Struct has necessary information to write PartitionUpdate in protobuf.
+  struct Partition {
+    // The name of the partition.
+    std::string name;
+
+    // The operations to be performed to this partition.
+    std::vector<AnnotatedOperation> aops;
+
+    PartitionInfo old_info;
+    PartitionInfo new_info;
+
+    PostInstallConfig postinstall;
+  };
+
+  std::vector<Partition> part_vec_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_FILE_H_
diff --git a/payload_generator/payload_file_unittest.cc b/payload_generator/payload_file_unittest.cc
new file mode 100644
index 0000000..4d18adf
--- /dev/null
+++ b/payload_generator/payload_file_unittest.cc
@@ -0,0 +1,94 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/payload_file.h"
+
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class PayloadFileTest : public ::testing::Test {
+ protected:
+  PayloadFile payload_;
+};
+
+TEST_F(PayloadFileTest, ReorderBlobsTest) {
+  string orig_blobs;
+  EXPECT_TRUE(utils::MakeTempFile("ReorderBlobsTest.orig.XXXXXX", &orig_blobs,
+                                  nullptr));
+  ScopedPathUnlinker orig_blobs_unlinker(orig_blobs);
+
+  // The operations have three blob and one gap (the whitespace):
+  // Rootfs operation 1: [8, 3] bcd
+  // Rootfs operation 2: [7, 1] a
+  // Kernel operation 1: [0, 6] kernel
+  string orig_data = "kernel abcd";
+  EXPECT_TRUE(
+      utils::WriteFile(orig_blobs.c_str(), orig_data.data(), orig_data.size()));
+
+  string new_blobs;
+  EXPECT_TRUE(
+      utils::MakeTempFile("ReorderBlobsTest.new.XXXXXX", &new_blobs, nullptr));
+  ScopedPathUnlinker new_blobs_unlinker(new_blobs);
+
+  payload_.part_vec_.resize(2);
+
+  vector<AnnotatedOperation> aops;
+  AnnotatedOperation aop;
+  aop.op.set_data_offset(8);
+  aop.op.set_data_length(3);
+  aops.push_back(aop);
+
+  aop.op.set_data_offset(7);
+  aop.op.set_data_length(1);
+  aops.push_back(aop);
+  payload_.part_vec_[0].aops = aops;
+
+  aop.op.set_data_offset(0);
+  aop.op.set_data_length(6);
+  payload_.part_vec_[1].aops = {aop};
+
+  EXPECT_TRUE(payload_.ReorderDataBlobs(orig_blobs, new_blobs));
+
+  const vector<AnnotatedOperation>& part0_aops = payload_.part_vec_[0].aops;
+  const vector<AnnotatedOperation>& part1_aops = payload_.part_vec_[1].aops;
+  string new_data;
+  EXPECT_TRUE(utils::ReadFile(new_blobs, &new_data));
+  // Kernel blobs should appear at the end.
+  EXPECT_EQ("bcdakernel", new_data);
+
+  EXPECT_EQ(2, part0_aops.size());
+  EXPECT_EQ(0, part0_aops[0].op.data_offset());
+  EXPECT_EQ(3, part0_aops[0].op.data_length());
+  EXPECT_EQ(3, part0_aops[1].op.data_offset());
+  EXPECT_EQ(1, part0_aops[1].op.data_length());
+
+  EXPECT_EQ(1, part1_aops.size());
+  EXPECT_EQ(4, part1_aops[0].op.data_offset());
+  EXPECT_EQ(6, part1_aops[0].op.data_length());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/payload_generation_config.cc b/payload_generator/payload_generation_config.cc
new file mode 100644
index 0000000..813e33c
--- /dev/null
+++ b/payload_generator/payload_generation_config.cc
@@ -0,0 +1,160 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/payload_generation_config.h"
+
+#include <base/logging.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/ext2_filesystem.h"
+#include "update_engine/payload_generator/raw_filesystem.h"
+
+namespace chromeos_update_engine {
+
+bool PostInstallConfig::IsEmpty() const {
+  return run == false && path.empty() && filesystem_type.empty();
+}
+
+bool PartitionConfig::ValidateExists() const {
+  TEST_AND_RETURN_FALSE(!path.empty());
+  TEST_AND_RETURN_FALSE(utils::FileExists(path.c_str()));
+  TEST_AND_RETURN_FALSE(size > 0);
+  // The requested size is within the limits of the file.
+  TEST_AND_RETURN_FALSE(static_cast<off_t>(size) <=
+                        utils::FileSize(path.c_str()));
+  // TODO(deymo): The delta generator algorithm doesn't support a block size
+  // different than 4 KiB. Remove this check once that's fixed. crbug.com/455045
+  int block_count, block_size;
+  if (utils::GetFilesystemSize(path, &block_count, &block_size) &&
+      block_size != 4096) {
+   LOG(ERROR) << "The filesystem provided in " << path
+              << " has a block size of " << block_size
+              << " but delta_generator only supports 4096.";
+   return false;
+  }
+  return true;
+}
+
+bool PartitionConfig::OpenFilesystem() {
+  if (path.empty())
+    return true;
+  fs_interface.reset();
+  if (utils::IsExtFilesystem(path)) {
+    fs_interface = Ext2Filesystem::CreateFromFile(path);
+  }
+
+  if (!fs_interface) {
+    // Fall back to a RAW filesystem.
+    TEST_AND_RETURN_FALSE(size % kBlockSize == 0);
+    fs_interface = RawFilesystem::Create(
+      "<" + name + "-partition>",
+      kBlockSize,
+      size / kBlockSize);
+  }
+  return true;
+}
+
+bool ImageConfig::ValidateIsEmpty() const {
+  TEST_AND_RETURN_FALSE(ImageInfoIsEmpty());
+  return partitions.empty();
+}
+
+bool ImageConfig::LoadImageSize() {
+  for (PartitionConfig& part : partitions) {
+    if (part.path.empty())
+      continue;
+    part.size = utils::FileSize(part.path);
+  }
+  return true;
+}
+
+bool ImageConfig::LoadPostInstallConfig(const brillo::KeyValueStore& store) {
+  bool found_postinstall = false;
+  for (PartitionConfig& part : partitions) {
+    bool run_postinstall;
+    if (!store.GetBoolean("RUN_POSTINSTALL_" + part.name, &run_postinstall) ||
+        !run_postinstall)
+      continue;
+    found_postinstall = true;
+    part.postinstall.run = true;
+    store.GetString("POSTINSTALL_PATH_" + part.name, &part.postinstall.path);
+    store.GetString("FILESYSTEM_TYPE_" + part.name,
+                    &part.postinstall.filesystem_type);
+  }
+  if (!found_postinstall) {
+    LOG(ERROR) << "No valid postinstall config found.";
+    return false;
+  }
+  return true;
+}
+
+bool ImageConfig::ImageInfoIsEmpty() const {
+  return image_info.board().empty()
+    && image_info.key().empty()
+    && image_info.channel().empty()
+    && image_info.version().empty()
+    && image_info.build_channel().empty()
+    && image_info.build_version().empty();
+}
+
+bool PayloadGenerationConfig::Validate() const {
+  if (is_delta) {
+    for (const PartitionConfig& part : source.partitions) {
+      if (!part.path.empty()) {
+        TEST_AND_RETURN_FALSE(part.ValidateExists());
+        TEST_AND_RETURN_FALSE(part.size % block_size == 0);
+      }
+      // Source partition should not have postinstall.
+      TEST_AND_RETURN_FALSE(part.postinstall.IsEmpty());
+    }
+
+    // Check for the supported minor_version values.
+    TEST_AND_RETURN_FALSE(minor_version == kInPlaceMinorPayloadVersion ||
+                          minor_version == kSourceMinorPayloadVersion ||
+                          minor_version == kOpSrcHashMinorPayloadVersion);
+
+    // If new_image_info is present, old_image_info must be present.
+    TEST_AND_RETURN_FALSE(source.ImageInfoIsEmpty() ==
+                          target.ImageInfoIsEmpty());
+  } else {
+    // All the "source" image fields must be empty for full payloads.
+    TEST_AND_RETURN_FALSE(source.ValidateIsEmpty());
+    TEST_AND_RETURN_FALSE(minor_version == kFullPayloadMinorVersion);
+  }
+
+  // In all cases, the target image must exists.
+  for (const PartitionConfig& part : target.partitions) {
+    TEST_AND_RETURN_FALSE(part.ValidateExists());
+    TEST_AND_RETURN_FALSE(part.size % block_size == 0);
+    if (minor_version == kInPlaceMinorPayloadVersion &&
+        part.name == kLegacyPartitionNameRoot)
+      TEST_AND_RETURN_FALSE(rootfs_partition_size >= part.size);
+    if (major_version == kChromeOSMajorPayloadVersion)
+      TEST_AND_RETURN_FALSE(part.postinstall.IsEmpty());
+  }
+
+  TEST_AND_RETURN_FALSE(hard_chunk_size == -1 ||
+                        hard_chunk_size % block_size == 0);
+  TEST_AND_RETURN_FALSE(soft_chunk_size % block_size == 0);
+
+  TEST_AND_RETURN_FALSE(rootfs_partition_size % block_size == 0);
+
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/payload_generation_config.h b/payload_generator/payload_generation_config.h
new file mode 100644
index 0000000..21bb89b
--- /dev/null
+++ b/payload_generator/payload_generation_config.h
@@ -0,0 +1,164 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_GENERATION_CONFIG_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_GENERATION_CONFIG_H_
+
+#include <cstddef>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include <brillo/key_value_store.h>
+
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_generator/filesystem_interface.h"
+#include "update_engine/update_metadata.pb.h"
+
+namespace chromeos_update_engine {
+
+struct PostInstallConfig {
+  // Whether the postinstall config is empty.
+  bool IsEmpty() const;
+
+  // Whether this partition carries a filesystem with post-install program that
+  // must be run to finalize the update process.
+  bool run = false;
+
+  // The path to the post-install program relative to the root of this
+  // filesystem.
+  std::string path;
+
+  // The filesystem type used to mount the partition in order to run the
+  // post-install program.
+  std::string filesystem_type;
+};
+
+struct PartitionConfig {
+  explicit PartitionConfig(std::string name) : name(name) {}
+
+  // Returns whether the PartitionConfig is not an empty image and all the
+  // fields are set correctly to a valid image file.
+  bool ValidateExists() const;
+
+  // Open then filesystem stored in this partition and stores it in
+  // |fs_interface|. Returns whether opening the filesystem worked.
+  bool OpenFilesystem();
+
+  // The path to the partition file. This can be a regular file or a block
+  // device such as a loop device.
+  std::string path;
+
+  // The size of the data in |path|. If rootfs verification is used (verity)
+  // this value should match the size of the verity device for the rootfs, and
+  // the size of the whole kernel. This value could be smaller than the
+  // partition and is the size of the data update_engine assumes verified for
+  // the source image, and the size of that data it should generate for the
+  // target image.
+  uint64_t size = 0;
+
+  // The FilesystemInterface implementation used to access this partition's
+  // files.
+  std::unique_ptr<FilesystemInterface> fs_interface;
+
+  std::string name;
+
+  PostInstallConfig postinstall;
+};
+
+// The ImageConfig struct describes a pair of binaries kernel and rootfs and the
+// metadata associated with the image they are part of, like build number, size,
+// etc.
+struct ImageConfig {
+  // Returns whether the ImageConfig is an empty image.
+  bool ValidateIsEmpty() const;
+
+  // Load |rootfs_size| and |kernel.size| from the respective image files. For
+  // the kernel, the whole |kernel.path| file is assumed. For the rootfs, the
+  // size is detected from the filesystem.
+  // Returns whether the image size was properly detected.
+  bool LoadImageSize();
+
+  // Load postinstall config from a key value store.
+  bool LoadPostInstallConfig(const brillo::KeyValueStore& store);
+
+  // Returns whether the |image_info| field is empty.
+  bool ImageInfoIsEmpty() const;
+
+  // The ImageInfo message defined in the update_metadata.proto file describes
+  // the metadata of the image.
+  ImageInfo image_info;
+
+  // The updated partitions.
+  std::vector<PartitionConfig> partitions;
+};
+
+// The PayloadGenerationConfig struct encapsulates all the configuration to
+// build the requested payload. This includes information about the old and new
+// image as well as the restrictions applied to the payload (like minor-version
+// and full/delta payload).
+struct PayloadGenerationConfig {
+  // Returns whether the PayloadGenerationConfig is valid.
+  bool Validate() const;
+
+  // Image information about the new image that's the target of this payload.
+  ImageConfig target;
+
+  // Image information pertaining the old image, if any. This is only valid
+  // if is_full is false, so we are requested a delta payload.
+  ImageConfig source;
+
+  // Wheter the requested payload is a delta payload.
+  bool is_delta = false;
+
+  // The major_version of the requested payload.
+  uint64_t major_version;
+
+  // The minor_version of the requested payload.
+  uint32_t minor_version;
+
+  // The size of the rootfs partition, that not necessarily is the same as the
+  // filesystem in either source or target version, since there is some space
+  // after the partition used to store the verity hashes and or the bootcache.
+  uint64_t rootfs_partition_size = 0;
+
+  // The |hard_chunk_size| is the maximum size that a single operation should
+  // write in the destination. Operations bigger than chunk_size should be
+  // split. A value of -1 means no hard chunk size limit. A very low limit
+  // means more operations, and less of a chance to reuse the data.
+  ssize_t hard_chunk_size = -1;
+
+  // The |soft_chunk_size| is the preferred chunk size to use when there's no
+  // significant impact to the operations. For example, REPLACE, MOVE and
+  // SOURCE_COPY operations are not significantly impacted by the chunk size,
+  // except for a few bytes overhead in the manifest to describe extra
+  // operations. On the other hand, splitting BSDIFF operations impacts the
+  // payload size since it is not possible to use the redundancy *between*
+  // chunks.
+  size_t soft_chunk_size = 2 * 1024 * 1024;
+
+  // TODO(deymo): Remove the block_size member and maybe replace it with a
+  // minimum alignment size for blocks (if needed). Algorithms should be able to
+  // pick the block_size they want, but for now only 4 KiB is supported.
+
+  // The block size used for all the operations in the manifest.
+  size_t block_size = 4096;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_GENERATION_CONFIG_H_
diff --git a/payload_generator/payload_generation_config_unittest.cc b/payload_generator/payload_generation_config_unittest.cc
new file mode 100644
index 0000000..122d94a
--- /dev/null
+++ b/payload_generator/payload_generation_config_unittest.cc
@@ -0,0 +1,52 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/payload_generation_config.h"
+
+#include <gtest/gtest.h>
+
+namespace chromeos_update_engine {
+
+class PayloadGenerationConfigTest : public ::testing::Test {};
+
+TEST_F(PayloadGenerationConfigTest, SimpleLoadPostInstallConfigTest) {
+  ImageConfig image_config;
+  image_config.partitions.emplace_back("root");
+  brillo::KeyValueStore store;
+  EXPECT_TRUE(
+      store.LoadFromString("RUN_POSTINSTALL_root=true\n"
+                           "POSTINSTALL_PATH_root=postinstall\n"
+                           "FILESYSTEM_TYPE_root=ext4"));
+  EXPECT_TRUE(image_config.LoadPostInstallConfig(store));
+  EXPECT_FALSE(image_config.partitions[0].postinstall.IsEmpty());
+  EXPECT_EQ(true, image_config.partitions[0].postinstall.run);
+  EXPECT_EQ("postinstall", image_config.partitions[0].postinstall.path);
+  EXPECT_EQ("ext4", image_config.partitions[0].postinstall.filesystem_type);
+}
+
+TEST_F(PayloadGenerationConfigTest, LoadPostInstallConfigNameMismatchTest) {
+  ImageConfig image_config;
+  image_config.partitions.emplace_back("system");
+  brillo::KeyValueStore store;
+  EXPECT_TRUE(
+      store.LoadFromString("RUN_POSTINSTALL_root=true\n"
+                           "POSTINSTALL_PATH_root=postinstall\n"
+                           "FILESYSTEM_TYPE_root=ext4"));
+  EXPECT_FALSE(image_config.LoadPostInstallConfig(store));
+  EXPECT_TRUE(image_config.partitions[0].postinstall.IsEmpty());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/payload_signer.cc b/payload_generator/payload_signer.cc
new file mode 100644
index 0000000..a0c61b1
--- /dev/null
+++ b/payload_generator/payload_signer.cc
@@ -0,0 +1,484 @@
+//
+// Copyright (C) 2011 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 "update_engine/payload_generator/payload_signer.h"
+
+#include <endian.h>
+
+#include <base/logging.h>
+#include <base/strings/string_split.h>
+#include <base/strings/string_util.h>
+#include <brillo/data_encoding.h>
+#include <openssl/pem.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/delta_performer.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_consumer/payload_verifier.h"
+#include "update_engine/payload_generator/delta_diff_generator.h"
+#include "update_engine/payload_generator/payload_file.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+
+// The payload verifier will check all the signatures included in the payload
+// regardless of the version field. Old version of the verifier require the
+// version field to be included and be 1.
+const uint32_t kSignatureMessageLegacyVersion = 1;
+
+// Given raw |signatures|, packs them into a protobuf and serializes it into a
+// binary blob. Returns true on success, false otherwise.
+bool ConvertSignatureToProtobufBlob(const vector<brillo::Blob>& signatures,
+                                    brillo::Blob* out_signature_blob) {
+  // Pack it into a protobuf
+  Signatures out_message;
+  for (const brillo::Blob& signature : signatures) {
+    Signatures_Signature* sig_message = out_message.add_signatures();
+    // Set all the signatures with the same version number.
+    sig_message->set_version(kSignatureMessageLegacyVersion);
+    sig_message->set_data(signature.data(), signature.size());
+  }
+
+  // Serialize protobuf
+  string serialized;
+  TEST_AND_RETURN_FALSE(out_message.AppendToString(&serialized));
+  out_signature_blob->insert(out_signature_blob->end(),
+                             serialized.begin(),
+                             serialized.end());
+  LOG(INFO) << "Signature blob size: " << out_signature_blob->size();
+  return true;
+}
+
+// Given an unsigned payload under |payload_path| and the |signature_blob| and
+// |metadata_signature_blob| generates an updated payload that includes the
+// signatures. It populates |out_metadata_size| with the size of the final
+// manifest after adding the dummy signature operation, and
+// |out_signatures_offset| with the expected offset for the new blob, and
+// |out_metadata_signature_size| which will be size of |metadata_signature_blob|
+// if the payload major version supports metadata signature, 0 otherwise.
+// Returns true on success, false otherwise.
+bool AddSignatureBlobToPayload(const string& payload_path,
+                               const brillo::Blob& signature_blob,
+                               const brillo::Blob& metadata_signature_blob,
+                               brillo::Blob* out_payload,
+                               uint64_t* out_metadata_size,
+                               uint32_t* out_metadata_signature_size,
+                               uint64_t* out_signatures_offset) {
+  uint64_t manifest_offset = 20;
+  const int kProtobufSizeOffset = 12;
+
+  // Loads the payload.
+  brillo::Blob payload;
+  DeltaArchiveManifest manifest;
+  uint64_t metadata_size, major_version;
+  uint32_t metadata_signature_size;
+  TEST_AND_RETURN_FALSE(PayloadSigner::LoadPayload(payload_path, &payload,
+      &manifest, &major_version, &metadata_size, &metadata_signature_size));
+
+  if (major_version == kBrilloMajorPayloadVersion) {
+    // Write metadata signature size in header.
+    uint32_t metadata_signature_size_be =
+        htobe32(metadata_signature_blob.size());
+    memcpy(payload.data() + manifest_offset, &metadata_signature_size_be,
+           sizeof(metadata_signature_size_be));
+    manifest_offset += sizeof(metadata_signature_size_be);
+    // Replace metadata signature.
+    payload.erase(payload.begin() + metadata_size,
+                  payload.begin() + metadata_size + metadata_signature_size);
+    payload.insert(payload.begin() + metadata_size,
+                   metadata_signature_blob.begin(),
+                   metadata_signature_blob.end());
+    metadata_signature_size = metadata_signature_blob.size();
+    LOG(INFO) << "Metadata signature size: " << metadata_signature_size;
+  }
+
+  // Is there already a signature op in place?
+  if (manifest.has_signatures_size()) {
+    // The signature op is tied to the size of the signature blob, but not it's
+    // contents. We don't allow the manifest to change if there is already an op
+    // present, because that might invalidate previously generated
+    // hashes/signatures.
+    if (manifest.signatures_size() != signature_blob.size()) {
+      LOG(ERROR) << "Attempt to insert different signature sized blob. "
+                 << "(current:" << manifest.signatures_size()
+                 << "new:" << signature_blob.size() << ")";
+      return false;
+    }
+
+    LOG(INFO) << "Matching signature sizes already present.";
+  } else {
+    // Updates the manifest to include the signature operation.
+    PayloadSigner::AddSignatureToManifest(
+        payload.size() - metadata_size - metadata_signature_size,
+        signature_blob.size(),
+        major_version == kChromeOSMajorPayloadVersion,
+        &manifest);
+
+    // Updates the payload to include the new manifest.
+    string serialized_manifest;
+    TEST_AND_RETURN_FALSE(manifest.AppendToString(&serialized_manifest));
+    LOG(INFO) << "Updated protobuf size: " << serialized_manifest.size();
+    payload.erase(payload.begin() + manifest_offset,
+                  payload.begin() + metadata_size);
+    payload.insert(payload.begin() + manifest_offset,
+                   serialized_manifest.begin(),
+                   serialized_manifest.end());
+
+    // Updates the protobuf size.
+    uint64_t size_be = htobe64(serialized_manifest.size());
+    memcpy(&payload[kProtobufSizeOffset], &size_be, sizeof(size_be));
+    metadata_size = serialized_manifest.size() + manifest_offset;
+
+    LOG(INFO) << "Updated payload size: " << payload.size();
+    LOG(INFO) << "Updated metadata size: " << metadata_size;
+  }
+  uint64_t signatures_offset = metadata_size + metadata_signature_size +
+                               manifest.signatures_offset();
+  LOG(INFO) << "Signature Blob Offset: " << signatures_offset;
+  payload.resize(signatures_offset);
+  payload.insert(payload.begin() + signatures_offset,
+                 signature_blob.begin(),
+                 signature_blob.end());
+
+  *out_payload = std::move(payload);
+  *out_metadata_size = metadata_size;
+  *out_metadata_signature_size = metadata_signature_size;
+  *out_signatures_offset = signatures_offset;
+  return true;
+}
+
+// Given a |payload| with correct signature op and metadata signature size in
+// header and |metadata_size|, |metadata_signature_size|, |signatures_offset|,
+// calculate hash for payload and metadata, save it to |out_hash_data| and
+// |out_metadata_hash|.
+bool CalculateHashFromPayload(const brillo::Blob& payload,
+                              const uint64_t metadata_size,
+                              const uint32_t metadata_signature_size,
+                              const uint64_t signatures_offset,
+                              brillo::Blob* out_hash_data,
+                              brillo::Blob* out_metadata_hash) {
+  if (out_metadata_hash) {
+    // Calculates the hash on the manifest.
+    TEST_AND_RETURN_FALSE(
+        HashCalculator::RawHashOfBytes(payload.data(), metadata_size,
+                                       out_metadata_hash));
+  }
+  if (out_hash_data) {
+    // Calculates the hash on the updated payload. Note that we skip metadata
+    // signature and payload signature.
+    HashCalculator calc;
+    TEST_AND_RETURN_FALSE(calc.Update(payload.data(), metadata_size));
+    TEST_AND_RETURN_FALSE(calc.Update(
+        payload.data() + metadata_size + metadata_signature_size,
+        signatures_offset - metadata_size - metadata_signature_size));
+    TEST_AND_RETURN_FALSE(calc.Finalize());
+    *out_hash_data = calc.raw_hash();
+  }
+  return true;
+}
+
+}  // namespace
+
+void PayloadSigner::AddSignatureToManifest(uint64_t signature_blob_offset,
+                                           uint64_t signature_blob_length,
+                                           bool add_dummy_op,
+                                           DeltaArchiveManifest* manifest) {
+  LOG(INFO) << "Making room for signature in file";
+  manifest->set_signatures_offset(signature_blob_offset);
+  LOG(INFO) << "set? " << manifest->has_signatures_offset();
+  manifest->set_signatures_offset(signature_blob_offset);
+  manifest->set_signatures_size(signature_blob_length);
+  // Add a dummy op at the end to appease older clients
+  if (add_dummy_op) {
+    InstallOperation* dummy_op = manifest->add_kernel_install_operations();
+    dummy_op->set_type(InstallOperation::REPLACE);
+    dummy_op->set_data_offset(signature_blob_offset);
+    dummy_op->set_data_length(signature_blob_length);
+    Extent* dummy_extent = dummy_op->add_dst_extents();
+    // Tell the dummy op to write this data to a big sparse hole
+    dummy_extent->set_start_block(kSparseHole);
+    dummy_extent->set_num_blocks((signature_blob_length + kBlockSize - 1) /
+                                 kBlockSize);
+  }
+}
+
+bool PayloadSigner::LoadPayload(const string& payload_path,
+                                brillo::Blob* out_payload,
+                                DeltaArchiveManifest* out_manifest,
+                                uint64_t* out_major_version,
+                                uint64_t* out_metadata_size,
+                                uint32_t* out_metadata_signature_size) {
+  brillo::Blob payload;
+  TEST_AND_RETURN_FALSE(utils::ReadFile(payload_path, &payload));
+  TEST_AND_RETURN_FALSE(payload.size() >=
+                        DeltaPerformer::kMaxPayloadHeaderSize);
+  const uint8_t* read_pointer = payload.data();
+  TEST_AND_RETURN_FALSE(
+      memcmp(read_pointer, kDeltaMagic, sizeof(kDeltaMagic)) == 0);
+  read_pointer += sizeof(kDeltaMagic);
+
+  uint64_t major_version;
+  memcpy(&major_version, read_pointer, sizeof(major_version));
+  read_pointer += sizeof(major_version);
+  major_version = be64toh(major_version);
+  TEST_AND_RETURN_FALSE(major_version == kChromeOSMajorPayloadVersion ||
+                        major_version == kBrilloMajorPayloadVersion);
+  if (out_major_version)
+    *out_major_version = major_version;
+
+  uint64_t manifest_size = 0;
+  memcpy(&manifest_size, read_pointer, sizeof(manifest_size));
+  read_pointer += sizeof(manifest_size);
+  manifest_size = be64toh(manifest_size);
+
+  uint32_t metadata_signature_size = 0;
+  if (major_version == kBrilloMajorPayloadVersion) {
+    memcpy(&metadata_signature_size, read_pointer,
+           sizeof(metadata_signature_size));
+    read_pointer += sizeof(metadata_signature_size);
+    metadata_signature_size = be32toh(metadata_signature_size);
+  }
+  if (out_metadata_signature_size)
+    *out_metadata_signature_size = metadata_signature_size;
+
+  *out_metadata_size = read_pointer - payload.data() + manifest_size;
+  TEST_AND_RETURN_FALSE(payload.size() >= *out_metadata_size);
+  if (out_manifest)
+    TEST_AND_RETURN_FALSE(
+        out_manifest->ParseFromArray(read_pointer, manifest_size));
+  *out_payload = std::move(payload);
+  return true;
+}
+
+bool PayloadSigner::VerifySignedPayload(const string& payload_path,
+                                        const string& public_key_path) {
+  brillo::Blob payload;
+  DeltaArchiveManifest manifest;
+  uint64_t metadata_size;
+  uint32_t metadata_signature_size;
+  TEST_AND_RETURN_FALSE(LoadPayload(payload_path, &payload, &manifest, nullptr,
+      &metadata_size, &metadata_signature_size));
+  TEST_AND_RETURN_FALSE(manifest.has_signatures_offset() &&
+                        manifest.has_signatures_size());
+  uint64_t signatures_offset = metadata_size + metadata_signature_size +
+                               manifest.signatures_offset();
+  CHECK_EQ(payload.size(), signatures_offset + manifest.signatures_size());
+  brillo::Blob payload_hash, metadata_hash;
+  TEST_AND_RETURN_FALSE(CalculateHashFromPayload(payload,
+                                                 metadata_size,
+                                                 metadata_signature_size,
+                                                 signatures_offset,
+                                                 &payload_hash,
+                                                 &metadata_hash));
+  brillo::Blob signature_blob(payload.begin() + signatures_offset,
+                              payload.end());
+  TEST_AND_RETURN_FALSE(PayloadVerifier::PadRSA2048SHA256Hash(&payload_hash));
+  TEST_AND_RETURN_FALSE(PayloadVerifier::VerifySignature(
+      signature_blob, public_key_path, payload_hash));
+  if (metadata_signature_size) {
+    signature_blob.assign(payload.begin() + metadata_size,
+                          payload.begin() + metadata_size +
+                          metadata_signature_size);
+    TEST_AND_RETURN_FALSE(
+        PayloadVerifier::PadRSA2048SHA256Hash(&metadata_hash));
+    TEST_AND_RETURN_FALSE(PayloadVerifier::VerifySignature(
+        signature_blob, public_key_path, metadata_hash));
+  }
+  return true;
+}
+
+bool PayloadSigner::SignHash(const brillo::Blob& hash,
+                             const string& private_key_path,
+                             brillo::Blob* out_signature) {
+  LOG(INFO) << "Signing hash with private key: " << private_key_path;
+  string sig_path;
+  TEST_AND_RETURN_FALSE(
+      utils::MakeTempFile("signature.XXXXXX", &sig_path, nullptr));
+  ScopedPathUnlinker sig_path_unlinker(sig_path);
+
+  string hash_path;
+  TEST_AND_RETURN_FALSE(
+      utils::MakeTempFile("hash.XXXXXX", &hash_path, nullptr));
+  ScopedPathUnlinker hash_path_unlinker(hash_path);
+  // We expect unpadded SHA256 hash coming in
+  TEST_AND_RETURN_FALSE(hash.size() == 32);
+  brillo::Blob padded_hash(hash);
+  PayloadVerifier::PadRSA2048SHA256Hash(&padded_hash);
+  TEST_AND_RETURN_FALSE(utils::WriteFile(hash_path.c_str(),
+                                         padded_hash.data(),
+                                         padded_hash.size()));
+
+  // This runs on the server, so it's okay to copy out and call openssl
+  // executable rather than properly use the library.
+  vector<string> cmd = {"openssl", "rsautl", "-raw", "-sign", "-inkey",
+                        private_key_path, "-in", hash_path, "-out", sig_path};
+  int return_code = 0;
+  TEST_AND_RETURN_FALSE(Subprocess::SynchronousExec(cmd, &return_code,
+                                                    nullptr));
+  TEST_AND_RETURN_FALSE(return_code == 0);
+
+  brillo::Blob signature;
+  TEST_AND_RETURN_FALSE(utils::ReadFile(sig_path, &signature));
+  out_signature->swap(signature);
+  return true;
+}
+
+bool PayloadSigner::SignHashWithKeys(const brillo::Blob& hash_data,
+                                     const vector<string>& private_key_paths,
+                                     brillo::Blob* out_signature_blob) {
+  vector<brillo::Blob> signatures;
+  for (const string& path : private_key_paths) {
+    brillo::Blob signature;
+    TEST_AND_RETURN_FALSE(SignHash(hash_data, path, &signature));
+    signatures.push_back(signature);
+  }
+  TEST_AND_RETURN_FALSE(ConvertSignatureToProtobufBlob(signatures,
+                                                       out_signature_blob));
+  return true;
+}
+
+bool PayloadSigner::SignPayload(const string& unsigned_payload_path,
+                                const vector<string>& private_key_paths,
+                                const uint64_t metadata_size,
+                                const uint32_t metadata_signature_size,
+                                const uint64_t signatures_offset,
+                                brillo::Blob* out_signature_blob) {
+  brillo::Blob payload;
+  TEST_AND_RETURN_FALSE(utils::ReadFile(unsigned_payload_path, &payload));
+  brillo::Blob hash_data;
+  TEST_AND_RETURN_FALSE(CalculateHashFromPayload(payload,
+                                                 metadata_size,
+                                                 metadata_signature_size,
+                                                 signatures_offset,
+                                                 &hash_data,
+                                                 nullptr));
+  TEST_AND_RETURN_FALSE(SignHashWithKeys(hash_data,
+                                         private_key_paths,
+                                         out_signature_blob));
+  return true;
+}
+
+bool PayloadSigner::SignatureBlobLength(const vector<string>& private_key_paths,
+                                        uint64_t* out_length) {
+  DCHECK(out_length);
+  brillo::Blob x_blob(1, 'x'), hash_blob, sig_blob;
+  TEST_AND_RETURN_FALSE(HashCalculator::RawHashOfBytes(x_blob.data(),
+                                                       x_blob.size(),
+                                                       &hash_blob));
+  TEST_AND_RETURN_FALSE(
+      SignHashWithKeys(hash_blob, private_key_paths, &sig_blob));
+  *out_length = sig_blob.size();
+  return true;
+}
+
+bool PayloadSigner::HashPayloadForSigning(const string& payload_path,
+                                          const vector<int>& signature_sizes,
+                                          brillo::Blob* out_payload_hash_data,
+                                          brillo::Blob* out_metadata_hash) {
+  // Create a signature blob with signatures filled with 0.
+  // Will be used for both payload signature and metadata signature.
+  vector<brillo::Blob> signatures;
+  for (int signature_size : signature_sizes) {
+    signatures.emplace_back(signature_size, 0);
+  }
+  brillo::Blob signature_blob;
+  TEST_AND_RETURN_FALSE(ConvertSignatureToProtobufBlob(signatures,
+                                                       &signature_blob));
+
+  brillo::Blob payload;
+  uint64_t metadata_size, signatures_offset;
+  uint32_t metadata_signature_size;
+  // Prepare payload for hashing.
+  TEST_AND_RETURN_FALSE(AddSignatureBlobToPayload(payload_path,
+                                                  signature_blob,
+                                                  signature_blob,
+                                                  &payload,
+                                                  &metadata_size,
+                                                  &metadata_signature_size,
+                                                  &signatures_offset));
+  TEST_AND_RETURN_FALSE(CalculateHashFromPayload(payload,
+                                                 metadata_size,
+                                                 metadata_signature_size,
+                                                 signatures_offset,
+                                                 out_payload_hash_data,
+                                                 out_metadata_hash));
+  return true;
+}
+
+bool PayloadSigner::AddSignatureToPayload(
+    const string& payload_path,
+    const vector<brillo::Blob>& payload_signatures,
+    const vector<brillo::Blob>& metadata_signatures,
+    const string& signed_payload_path,
+    uint64_t *out_metadata_size) {
+  // TODO(petkov): Reduce memory usage -- the payload is manipulated in memory.
+
+  // Loads the payload and adds the signature op to it.
+  brillo::Blob signature_blob, metadata_signature_blob;
+  TEST_AND_RETURN_FALSE(ConvertSignatureToProtobufBlob(payload_signatures,
+                                                       &signature_blob));
+  if (!metadata_signatures.empty()) {
+    TEST_AND_RETURN_FALSE(
+        ConvertSignatureToProtobufBlob(metadata_signatures,
+                                       &metadata_signature_blob));
+  }
+  brillo::Blob payload;
+  uint64_t signatures_offset;
+  uint32_t metadata_signature_size;
+  TEST_AND_RETURN_FALSE(AddSignatureBlobToPayload(payload_path,
+                                                  signature_blob,
+                                                  metadata_signature_blob,
+                                                  &payload,
+                                                  out_metadata_size,
+                                                  &metadata_signature_size,
+                                                  &signatures_offset));
+
+  LOG(INFO) << "Signed payload size: " << payload.size();
+  TEST_AND_RETURN_FALSE(utils::WriteFile(signed_payload_path.c_str(),
+                                         payload.data(),
+                                         payload.size()));
+  return true;
+}
+
+bool PayloadSigner::GetMetadataSignature(const void* const metadata,
+                                         size_t metadata_size,
+                                         const string& private_key_path,
+                                         string* out_signature) {
+  // Calculates the hash on the updated payload. Note that the payload includes
+  // the signature op but doesn't include the signature blob at the end.
+  brillo::Blob metadata_hash;
+  TEST_AND_RETURN_FALSE(HashCalculator::RawHashOfBytes(metadata,
+                                                       metadata_size,
+                                                       &metadata_hash));
+
+  brillo::Blob signature;
+  TEST_AND_RETURN_FALSE(SignHash(metadata_hash,
+                                 private_key_path,
+                                 &signature));
+
+  *out_signature = brillo::data_encoding::Base64Encode(signature);
+  return true;
+}
+
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/payload_signer.h b/payload_generator/payload_signer.h
new file mode 100644
index 0000000..e7351dd
--- /dev/null
+++ b/payload_generator/payload_signer.h
@@ -0,0 +1,142 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_SIGNER_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_SIGNER_H_
+
+#include <string>
+#include <vector>
+
+#include <base/macros.h>
+#include <brillo/secure_blob.h>
+
+#include "update_engine/update_metadata.pb.h"
+
+// This class encapsulates methods used for payload signing.
+// See update_metadata.proto for more info.
+
+namespace chromeos_update_engine {
+
+class PayloadSigner {
+ public:
+  // Reads the payload from the given |payload_path| into the |out_payload|
+  // vector. It also parses the manifest protobuf in the payload and returns it
+  // in |out_manifest| if not null, along with the major version of the payload
+  // in |out_major_version| if not null, the size of the entire metadata in
+  // |out_metadata_size| and the size of metadata signature in
+  // |out_metadata_signature_size| if not null.
+  static bool LoadPayload(const std::string& payload_path,
+                          brillo::Blob* out_payload,
+                          DeltaArchiveManifest* out_manifest,
+                          uint64_t* out_major_version,
+                          uint64_t* out_metadata_size,
+                          uint32_t* out_metadata_signature_size);
+
+  // Returns true if the payload in |payload_path| is signed and its hash can be
+  // verified using the public key in |public_key_path| with the signature
+  // of a given version in the signature blob. Returns false otherwise.
+  static bool VerifySignedPayload(const std::string& payload_path,
+                                  const std::string& public_key_path);
+
+  // Adds specified signature offset/length to given |manifest|, also adds a
+  // dummy operation that points to a signature blob located at the specified
+  // offset/length if |add_dummy_op| is true.
+  static void AddSignatureToManifest(uint64_t signature_blob_offset,
+                                     uint64_t signature_blob_length,
+                                     bool add_dummy_op,
+                                     DeltaArchiveManifest* manifest);
+
+  // Given a raw |hash| and a private key in |private_key_path| calculates the
+  // raw signature in |out_signature|. Returns true on success, false otherwise.
+  static bool SignHash(const brillo::Blob& hash,
+                       const std::string& private_key_path,
+                       brillo::Blob* out_signature);
+
+  // Sign |hash_data| blob with all private keys in |private_key_paths|, then
+  // convert the signatures to protobuf blob.
+  static bool SignHashWithKeys(
+      const brillo::Blob& hash_data,
+      const std::vector<std::string>& private_key_paths,
+      brillo::Blob* out_signature_blob);
+
+  // Given an unsigned payload in |unsigned_payload_path|, private keys in
+  // |private_key_path|, metadata size in |metadata_size|, metadata signature
+  // size in |metadata_signature_size| and signatures offset in
+  // |signatures_offset|, calculates the payload signature blob into
+  // |out_signature_blob|. Note that the payload must already have an
+  // updated manifest that includes the dummy signature op and correct metadata
+  // signature size in header. Returns true on success, false otherwise.
+  static bool SignPayload(const std::string& unsigned_payload_path,
+                          const std::vector<std::string>& private_key_paths,
+                          const uint64_t metadata_size,
+                          const uint32_t metadata_signature_size,
+                          const uint64_t signatures_offset,
+                          brillo::Blob* out_signature_blob);
+
+  // Returns the length of out_signature_blob that will result in a call
+  // to SignPayload with the given private keys. Returns true on success.
+  static bool SignatureBlobLength(
+      const std::vector<std::string>& private_key_paths,
+      uint64_t* out_length);
+
+  // Given an unsigned payload in |payload_path|,
+  // this method does two things:
+  // 1. It loads the payload into memory, and inserts placeholder signature
+  //    operations and placeholder metadata signature to make the header and
+  //    the manifest match what the final signed payload will look like based
+  //    on |signatures_sizes|, if needed.
+  // 2. It calculates the raw SHA256 hash of the payload and the metadata in
+  //    |payload_path| (except signatures) and returns the result in
+  //    |out_hash_data| and |out_metadata_hash| respectively.
+  //
+  // The changes to payload are not preserved or written to disk.
+  static bool HashPayloadForSigning(const std::string& payload_path,
+                                    const std::vector<int>& signature_sizes,
+                                    brillo::Blob* out_payload_hash_data,
+                                    brillo::Blob* out_metadata_hash);
+
+  // Given an unsigned payload in |payload_path| (with no dummy signature op)
+  // and the raw |payload_signatures| and |metadata_signatures| updates the
+  // payload to include the signature thus turning it into a signed payload. The
+  // new payload is stored in |signed_payload_path|. |payload_path| and
+  // |signed_payload_path| can point to the same file. Populates
+  // |out_metadata_size| with the size of the metadata after adding the
+  // signature operation in the manifest. Returns true on success, false
+  // otherwise.
+  static bool AddSignatureToPayload(
+      const std::string& payload_path,
+      const std::vector<brillo::Blob>& payload_signatures,
+      const std::vector<brillo::Blob>& metadata_signatures,
+      const std::string& signed_payload_path,
+      uint64_t* out_metadata_size);
+
+  // Computes the SHA256 hash of the first metadata_size bytes of |metadata|
+  // and signs the hash with the given private_key_path and writes the signed
+  // hash in |out_signature|. Returns true if successful or false if there was
+  // any error in the computations.
+  static bool GetMetadataSignature(const void* const metadata,
+                                   size_t metadata_size,
+                                   const std::string& private_key_path,
+                                   std::string* out_signature);
+
+ private:
+  // This should never be constructed
+  DISALLOW_IMPLICIT_CONSTRUCTORS(PayloadSigner);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_PAYLOAD_SIGNER_H_
diff --git a/payload_generator/payload_signer_unittest.cc b/payload_generator/payload_signer_unittest.cc
new file mode 100644
index 0000000..b302f52
--- /dev/null
+++ b/payload_generator/payload_signer_unittest.cc
@@ -0,0 +1,245 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/payload_signer.h"
+
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/hash_calculator.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_consumer/payload_verifier.h"
+#include "update_engine/payload_generator/payload_file.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::string;
+using std::vector;
+
+// Note: the test key was generated with the following command:
+// openssl genrsa -out unittest_key.pem 2048
+// The public-key version is created by the build system.
+
+namespace chromeos_update_engine {
+
+const char* kUnittestPrivateKeyPath = "unittest_key.pem";
+const char* kUnittestPublicKeyPath = "unittest_key.pub.pem";
+const char* kUnittestPrivateKey2Path = "unittest_key2.pem";
+const char* kUnittestPublicKey2Path = "unittest_key2.pub.pem";
+
+// Some data and its corresponding hash and signature:
+const char kDataToSign[] = "This is some data to sign.";
+
+// Generated by:
+// echo -n 'This is some data to sign.' | openssl dgst -sha256 -binary |
+//   hexdump -v -e '" " 8/1 "0x%02x, " "\n"'
+const uint8_t kDataHash[] = {
+  0x7a, 0x07, 0xa6, 0x44, 0x08, 0x86, 0x20, 0xa6,
+  0xc1, 0xf8, 0xd9, 0x02, 0x05, 0x63, 0x0d, 0xb7,
+  0xfc, 0x2b, 0xa0, 0xa9, 0x7c, 0x9d, 0x1d, 0x8c,
+  0x01, 0xf5, 0x78, 0x6d, 0xc5, 0x11, 0xb4, 0x06
+};
+
+// Generated with openssl 1.0, which at the time of this writing, you need
+// to download and install yourself. Here's my command:
+// echo -n 'This is some data to sign.' | openssl dgst -sha256 -binary |
+//    ~/local/bin/openssl pkeyutl -sign -inkey unittest_key.pem -pkeyopt
+//    digest:sha256 | hexdump -v -e '" " 8/1 "0x%02x, " "\n"'
+const uint8_t kDataSignature[] = {
+  0x9f, 0x86, 0x25, 0x8b, 0xf3, 0xcc, 0xe3, 0x95,
+  0x5f, 0x45, 0x83, 0xb2, 0x66, 0xf0, 0x2a, 0xcf,
+  0xb7, 0xaa, 0x52, 0x25, 0x7a, 0xdd, 0x9d, 0x65,
+  0xe5, 0xd6, 0x02, 0x4b, 0x37, 0x99, 0x53, 0x06,
+  0xc2, 0xc9, 0x37, 0x36, 0x25, 0x62, 0x09, 0x4f,
+  0x6b, 0x22, 0xf8, 0xb3, 0x89, 0x14, 0x98, 0x1a,
+  0xbc, 0x30, 0x90, 0x4a, 0x43, 0xf5, 0xea, 0x2e,
+  0xf0, 0xa4, 0xba, 0xc3, 0xa7, 0xa3, 0x44, 0x70,
+  0xd6, 0xc4, 0x89, 0xd8, 0x45, 0x71, 0xbb, 0xee,
+  0x59, 0x87, 0x3d, 0xd5, 0xe5, 0x40, 0x22, 0x3d,
+  0x73, 0x7e, 0x2a, 0x58, 0x93, 0x8e, 0xcb, 0x9c,
+  0xf2, 0xbb, 0x4a, 0xc9, 0xd2, 0x2c, 0x52, 0x42,
+  0xb0, 0xd1, 0x13, 0x22, 0xa4, 0x78, 0xc7, 0xc6,
+  0x3e, 0xf1, 0xdc, 0x4c, 0x7b, 0x2d, 0x40, 0xda,
+  0x58, 0xac, 0x4a, 0x11, 0x96, 0x3d, 0xa0, 0x01,
+  0xf6, 0x96, 0x74, 0xf6, 0x6c, 0x0c, 0x49, 0x69,
+  0x4e, 0xc1, 0x7e, 0x9f, 0x2a, 0x42, 0xdd, 0x15,
+  0x6b, 0x37, 0x2e, 0x3a, 0xa7, 0xa7, 0x6d, 0x91,
+  0x13, 0xe8, 0x59, 0xde, 0xfe, 0x99, 0x07, 0xd9,
+  0x34, 0x0f, 0x17, 0xb3, 0x05, 0x4c, 0xd2, 0xc6,
+  0x82, 0xb7, 0x38, 0x36, 0x63, 0x1d, 0x9e, 0x21,
+  0xa6, 0x32, 0xef, 0xf1, 0x65, 0xe6, 0xed, 0x95,
+  0x25, 0x9b, 0x61, 0xe0, 0xba, 0x86, 0xa1, 0x7f,
+  0xf8, 0xa5, 0x4a, 0x32, 0x1f, 0x15, 0x20, 0x8a,
+  0x41, 0xc5, 0xb0, 0xd9, 0x4a, 0xda, 0x85, 0xf3,
+  0xdc, 0xa0, 0x98, 0x5d, 0x1d, 0x18, 0x9d, 0x2e,
+  0x42, 0xea, 0x69, 0x13, 0x74, 0x3c, 0x74, 0xf7,
+  0x6d, 0x43, 0xb0, 0x63, 0x90, 0xdb, 0x04, 0xd5,
+  0x05, 0xc9, 0x73, 0x1f, 0x6c, 0xd6, 0xfa, 0x46,
+  0x4e, 0x0f, 0x33, 0x58, 0x5b, 0x0d, 0x1b, 0x55,
+  0x39, 0xb9, 0x0f, 0x43, 0x37, 0xc0, 0x06, 0x0c,
+  0x29, 0x93, 0x43, 0xc7, 0x43, 0xb9, 0xab, 0x7d
+};
+
+namespace {
+void SignSampleData(brillo::Blob* out_signature_blob,
+                    const vector<string>& private_keys) {
+  brillo::Blob data_blob(std::begin(kDataToSign),
+                         std::begin(kDataToSign) + strlen(kDataToSign));
+  uint64_t length = 0;
+  EXPECT_TRUE(PayloadSigner::SignatureBlobLength(private_keys, &length));
+  EXPECT_GT(length, 0);
+  brillo::Blob hash_blob;
+  EXPECT_TRUE(HashCalculator::RawHashOfBytes(data_blob.data(),
+                                             data_blob.size(),
+                                             &hash_blob));
+  EXPECT_TRUE(PayloadSigner::SignHashWithKeys(
+      hash_blob,
+      private_keys,
+      out_signature_blob));
+  EXPECT_EQ(length, out_signature_blob->size());
+}
+}  // namespace
+
+class PayloadSignerTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    PayloadVerifier::PadRSA2048SHA256Hash(&padded_hash_data_);
+  }
+
+  void DoWriteAndLoadPayloadTest(const PayloadGenerationConfig& config) {
+    PayloadFile payload;
+    payload.Init(config);
+    string payload_path;
+    EXPECT_TRUE(utils::MakeTempFile("payload.XXXXXX", &payload_path, nullptr));
+    ScopedPathUnlinker payload_path_unlinker(payload_path);
+    uint64_t metadata_size;
+    EXPECT_TRUE(
+        payload.WritePayload(payload_path, "/dev/null", "", &metadata_size));
+    brillo::Blob payload_blob;
+    DeltaArchiveManifest manifest;
+    uint64_t load_metadata_size, load_major_version;
+    EXPECT_TRUE(PayloadSigner::LoadPayload(payload_path, &payload_blob,
+        &manifest, &load_major_version, &load_metadata_size, nullptr));
+    EXPECT_EQ(utils::FileSize(payload_path), payload_blob.size());
+    EXPECT_EQ(config.major_version, load_major_version);
+    EXPECT_EQ(metadata_size, load_metadata_size);
+  }
+
+  brillo::Blob padded_hash_data_{std::begin(kDataHash), std::end(kDataHash)};
+};
+
+TEST_F(PayloadSignerTest, LoadPayloadV1Test) {
+  PayloadGenerationConfig config;
+  config.major_version = kChromeOSMajorPayloadVersion;
+  DoWriteAndLoadPayloadTest(config);
+}
+
+TEST_F(PayloadSignerTest, LoadPayloadV2Test) {
+  PayloadGenerationConfig config;
+  config.major_version = kBrilloMajorPayloadVersion;
+  DoWriteAndLoadPayloadTest(config);
+}
+
+TEST_F(PayloadSignerTest, SignSimpleTextTest) {
+  brillo::Blob signature_blob;
+  SignSampleData(&signature_blob, {kUnittestPrivateKeyPath});
+
+  // Check the signature itself
+  Signatures signatures;
+  EXPECT_TRUE(signatures.ParseFromArray(signature_blob.data(),
+                                        signature_blob.size()));
+  EXPECT_EQ(1, signatures.signatures_size());
+  const Signatures_Signature& signature = signatures.signatures(0);
+  EXPECT_EQ(1, signature.version());
+  const string sig_data = signature.data();
+  ASSERT_EQ(arraysize(kDataSignature), sig_data.size());
+  for (size_t i = 0; i < arraysize(kDataSignature); i++) {
+    EXPECT_EQ(kDataSignature[i], static_cast<uint8_t>(sig_data[i]));
+  }
+}
+
+TEST_F(PayloadSignerTest, VerifyAllSignatureTest) {
+  brillo::Blob signature_blob;
+  SignSampleData(&signature_blob,
+                 {kUnittestPrivateKeyPath, kUnittestPrivateKey2Path});
+
+  // Either public key should pass the verification.
+  EXPECT_TRUE(PayloadVerifier::VerifySignature(signature_blob,
+                                               kUnittestPublicKeyPath,
+                                               padded_hash_data_));
+  EXPECT_TRUE(PayloadVerifier::VerifySignature(signature_blob,
+                                               kUnittestPublicKey2Path,
+                                               padded_hash_data_));
+}
+
+TEST_F(PayloadSignerTest, VerifySignatureTest) {
+  brillo::Blob signature_blob;
+  SignSampleData(&signature_blob, {kUnittestPrivateKeyPath});
+
+  EXPECT_TRUE(PayloadVerifier::VerifySignature(signature_blob,
+                                               kUnittestPublicKeyPath,
+                                               padded_hash_data_));
+  // Passing the invalid key should fail the verification.
+  EXPECT_FALSE(PayloadVerifier::VerifySignature(signature_blob,
+                                                kUnittestPublicKey2Path,
+                                                padded_hash_data_));
+}
+
+TEST_F(PayloadSignerTest, SkipMetadataSignatureTest) {
+  string payload_path;
+  EXPECT_TRUE(utils::MakeTempFile("payload.XXXXXX", &payload_path, nullptr));
+  ScopedPathUnlinker payload_path_unlinker(payload_path);
+
+  PayloadGenerationConfig config;
+  config.major_version = kBrilloMajorPayloadVersion;
+  PayloadFile payload;
+  EXPECT_TRUE(payload.Init(config));
+  uint64_t metadata_size;
+  EXPECT_TRUE(
+      payload.WritePayload(payload_path, "/dev/null", "", &metadata_size));
+  const vector<int> sizes = {256};
+  brillo::Blob unsigned_payload_hash, unsigned_metadata_hash;
+  EXPECT_TRUE(PayloadSigner::HashPayloadForSigning(
+      payload_path, sizes, &unsigned_payload_hash, &unsigned_metadata_hash));
+  EXPECT_TRUE(payload.WritePayload(
+      payload_path, "/dev/null", kUnittestPrivateKeyPath, &metadata_size));
+  brillo::Blob signed_payload_hash, signed_metadata_hash;
+  EXPECT_TRUE(PayloadSigner::HashPayloadForSigning(
+      payload_path, sizes, &signed_payload_hash, &signed_metadata_hash));
+  EXPECT_EQ(unsigned_payload_hash, signed_payload_hash);
+  EXPECT_EQ(unsigned_metadata_hash, signed_metadata_hash);
+}
+
+TEST_F(PayloadSignerTest, VerifySignedPayloadTest) {
+  string payload_path;
+  EXPECT_TRUE(utils::MakeTempFile("payload.XXXXXX", &payload_path, nullptr));
+  ScopedPathUnlinker payload_path_unlinker(payload_path);
+
+  PayloadGenerationConfig config;
+  config.major_version = kBrilloMajorPayloadVersion;
+  PayloadFile payload;
+  EXPECT_TRUE(payload.Init(config));
+  uint64_t metadata_size;
+  EXPECT_TRUE(payload.WritePayload(
+      payload_path, "/dev/null", kUnittestPrivateKeyPath, &metadata_size));
+  EXPECT_TRUE(PayloadSigner::VerifySignedPayload(payload_path,
+                                                 kUnittestPublicKeyPath));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/raw_filesystem.cc b/payload_generator/raw_filesystem.cc
new file mode 100644
index 0000000..2fb1400
--- /dev/null
+++ b/payload_generator/raw_filesystem.cc
@@ -0,0 +1,53 @@
+//
+// Copyright (C) 2015 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 "update_engine/payload_generator/raw_filesystem.h"
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/extent_ranges.h"
+#include "update_engine/update_metadata.pb.h"
+
+using std::unique_ptr;
+
+namespace chromeos_update_engine {
+
+unique_ptr<RawFilesystem> RawFilesystem::Create(
+      const std::string& filename, uint64_t block_size, uint64_t block_count) {
+  unique_ptr<RawFilesystem> result(new RawFilesystem());
+  result->filename_ = filename;
+  result->block_size_ = block_size;
+  result->block_count_ = block_count;
+  return result;
+}
+
+size_t RawFilesystem::GetBlockSize() const {
+  return block_size_;
+}
+
+size_t RawFilesystem::GetBlockCount() const {
+  return block_count_;
+}
+
+bool RawFilesystem::GetFiles(std::vector<File>* files) const {
+  files->clear();
+  File file;
+  file.name = filename_;
+  file.extents = { ExtentForRange(0, block_count_) };
+  files->push_back(file);
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/raw_filesystem.h b/payload_generator/raw_filesystem.h
new file mode 100644
index 0000000..0aecd81
--- /dev/null
+++ b/payload_generator/raw_filesystem.h
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_RAW_FILESYSTEM_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_RAW_FILESYSTEM_H_
+
+// A simple filesystem interface implementation used for unknown filesystem
+// format such as the kernel.
+
+#include "update_engine/payload_generator/filesystem_interface.h"
+
+#include <string>
+#include <vector>
+
+namespace chromeos_update_engine {
+
+class RawFilesystem : public FilesystemInterface {
+ public:
+  static std::unique_ptr<RawFilesystem> Create(
+      const std::string& filename, uint64_t block_size, uint64_t block_count);
+  virtual ~RawFilesystem() = default;
+
+  // FilesystemInterface overrides.
+  size_t GetBlockSize() const override;
+  size_t GetBlockCount() const override;
+
+  // GetFiles will return only one file with all the blocks of the filesystem
+  // with the name passed during construction.
+  bool GetFiles(std::vector<File>* files) const override;
+
+  bool LoadSettings(brillo::KeyValueStore* store) const override {
+    return false;
+  }
+
+ private:
+  RawFilesystem() = default;
+
+  std::string filename_;
+  uint64_t block_count_;
+  uint64_t block_size_;
+
+  DISALLOW_COPY_AND_ASSIGN(RawFilesystem);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_RAW_FILESYSTEM_H_
diff --git a/payload_generator/tarjan.cc b/payload_generator/tarjan.cc
new file mode 100644
index 0000000..98e29f9
--- /dev/null
+++ b/payload_generator/tarjan.cc
@@ -0,0 +1,83 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/tarjan.h"
+
+#include <algorithm>
+#include <vector>
+
+#include <base/logging.h>
+
+#include "update_engine/common/utils.h"
+
+using std::min;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+const vector<Vertex>::size_type kInvalidIndex = -1;
+}
+
+void TarjanAlgorithm::Execute(Vertex::Index vertex,
+                              Graph* graph,
+                              vector<Vertex::Index>* out) {
+  stack_.clear();
+  components_.clear();
+  index_ = 0;
+  for (Graph::iterator it = graph->begin(); it != graph->end(); ++it)
+    it->index = it->lowlink = kInvalidIndex;
+  required_vertex_ = vertex;
+
+  Tarjan(vertex, graph);
+  if (!components_.empty())
+    out->swap(components_[0]);
+}
+
+void TarjanAlgorithm::Tarjan(Vertex::Index vertex, Graph* graph) {
+  CHECK_EQ((*graph)[vertex].index, kInvalidIndex);
+  (*graph)[vertex].index = index_;
+  (*graph)[vertex].lowlink = index_;
+  index_++;
+  stack_.push_back(vertex);
+  for (Vertex::EdgeMap::iterator it = (*graph)[vertex].out_edges.begin();
+       it != (*graph)[vertex].out_edges.end(); ++it) {
+    Vertex::Index vertex_next = it->first;
+    if ((*graph)[vertex_next].index == kInvalidIndex) {
+      Tarjan(vertex_next, graph);
+      (*graph)[vertex].lowlink = min((*graph)[vertex].lowlink,
+                                     (*graph)[vertex_next].lowlink);
+    } else if (utils::VectorContainsValue(stack_, vertex_next)) {
+      (*graph)[vertex].lowlink = min((*graph)[vertex].lowlink,
+                                     (*graph)[vertex_next].index);
+    }
+  }
+  if ((*graph)[vertex].lowlink == (*graph)[vertex].index) {
+    vector<Vertex::Index> component;
+    Vertex::Index other_vertex;
+    do {
+      other_vertex = stack_.back();
+      stack_.pop_back();
+      component.push_back(other_vertex);
+    } while (other_vertex != vertex && !stack_.empty());
+
+    if (utils::VectorContainsValue(component, required_vertex_)) {
+      components_.resize(components_.size() + 1);
+      component.swap(components_.back());
+    }
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/tarjan.h b/payload_generator/tarjan.h
new file mode 100644
index 0000000..50cf563
--- /dev/null
+++ b/payload_generator/tarjan.h
@@ -0,0 +1,52 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_TARJAN_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_TARJAN_H_
+
+// This is an implementation of Tarjan's algorithm which finds all
+// Strongly Connected Components in a graph.
+
+// Note: a true Tarjan algorithm would find all strongly connected components
+// in the graph. This implementation will only find the strongly connected
+// component containing the vertex passed in.
+
+#include <vector>
+
+#include "update_engine/payload_generator/graph_types.h"
+
+namespace chromeos_update_engine {
+
+class TarjanAlgorithm {
+ public:
+  TarjanAlgorithm() : index_(0), required_vertex_(0) {}
+
+  // 'out' is set to the result if there is one, otherwise it's untouched.
+  void Execute(Vertex::Index vertex,
+               Graph* graph,
+               std::vector<Vertex::Index>* out);
+ private:
+  void Tarjan(Vertex::Index vertex, Graph* graph);
+
+  Vertex::Index index_;
+  Vertex::Index required_vertex_;
+  std::vector<Vertex::Index> stack_;
+  std::vector<std::vector<Vertex::Index>> components_;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_TARJAN_H_
diff --git a/payload_generator/tarjan_unittest.cc b/payload_generator/tarjan_unittest.cc
new file mode 100644
index 0000000..e40a7ff
--- /dev/null
+++ b/payload_generator/tarjan_unittest.cc
@@ -0,0 +1,94 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/tarjan.h"
+
+#include <string>
+#include <utility>
+
+#include <base/logging.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/payload_generator/graph_types.h"
+
+using std::make_pair;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class TarjanAlgorithmTest : public ::testing::Test {};
+
+TEST(TarjanAlgorithmTest, SimpleTest) {
+  const Vertex::Index n_a = 0;
+  const Vertex::Index n_b = 1;
+  const Vertex::Index n_c = 2;
+  const Vertex::Index n_d = 3;
+  const Vertex::Index n_e = 4;
+  const Vertex::Index n_f = 5;
+  const Vertex::Index n_g = 6;
+  const Vertex::Index n_h = 7;
+  const Graph::size_type kNodeCount = 8;
+
+  Graph graph(kNodeCount);
+
+  graph[n_a].out_edges.insert(make_pair(n_e, EdgeProperties()));
+  graph[n_a].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_b].out_edges.insert(make_pair(n_a, EdgeProperties()));
+  graph[n_c].out_edges.insert(make_pair(n_d, EdgeProperties()));
+  graph[n_d].out_edges.insert(make_pair(n_e, EdgeProperties()));
+  graph[n_d].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_b, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_c, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_f].out_edges.insert(make_pair(n_g, EdgeProperties()));
+  graph[n_g].out_edges.insert(make_pair(n_h, EdgeProperties()));
+  graph[n_h].out_edges.insert(make_pair(n_g, EdgeProperties()));
+
+  TarjanAlgorithm tarjan;
+
+  for (Vertex::Index i = n_a; i <= n_e; i++) {
+    vector<Vertex::Index> vertex_indexes;
+    tarjan.Execute(i, &graph, &vertex_indexes);
+
+    EXPECT_EQ(5, vertex_indexes.size());
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_a));
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_b));
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_c));
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_d));
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_e));
+  }
+
+  {
+    vector<Vertex::Index> vertex_indexes;
+    tarjan.Execute(n_f, &graph, &vertex_indexes);
+
+    EXPECT_EQ(1, vertex_indexes.size());
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_f));
+  }
+
+  for (Vertex::Index i = n_g; i <= n_h; i++) {
+    vector<Vertex::Index> vertex_indexes;
+    tarjan.Execute(i, &graph, &vertex_indexes);
+
+    EXPECT_EQ(2, vertex_indexes.size());
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_g));
+    EXPECT_TRUE(utils::VectorContainsValue(vertex_indexes, n_h));
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/topological_sort.cc b/payload_generator/topological_sort.cc
new file mode 100644
index 0000000..f164336
--- /dev/null
+++ b/payload_generator/topological_sort.cc
@@ -0,0 +1,56 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/topological_sort.h"
+
+#include <set>
+#include <vector>
+
+#include <base/logging.h>
+
+using std::set;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+namespace {
+void TopologicalSortVisit(const Graph& graph,
+                          set<Vertex::Index>* visited_nodes,
+                          vector<Vertex::Index>* nodes,
+                          Vertex::Index node) {
+  if (visited_nodes->find(node) != visited_nodes->end())
+    return;
+
+  visited_nodes->insert(node);
+  // Visit all children.
+  for (Vertex::EdgeMap::const_iterator it = graph[node].out_edges.begin();
+       it != graph[node].out_edges.end(); ++it) {
+    TopologicalSortVisit(graph, visited_nodes, nodes, it->first);
+  }
+  // Visit this node.
+  nodes->push_back(node);
+}
+}  // namespace
+
+void TopologicalSort(const Graph& graph, vector<Vertex::Index>* out) {
+  set<Vertex::Index> visited_nodes;
+
+  for (Vertex::Index i = 0; i < graph.size(); i++) {
+    TopologicalSortVisit(graph, &visited_nodes, out, i);
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/topological_sort.h b/payload_generator/topological_sort.h
new file mode 100644
index 0000000..461cbe1
--- /dev/null
+++ b/payload_generator/topological_sort.h
@@ -0,0 +1,42 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_GENERATOR_TOPOLOGICAL_SORT_H_
+#define UPDATE_ENGINE_PAYLOAD_GENERATOR_TOPOLOGICAL_SORT_H_
+
+#include <vector>
+
+#include "update_engine/payload_generator/graph_types.h"
+
+namespace chromeos_update_engine {
+
+// Performs a topological sort on the directed graph 'graph' and stores
+// the nodes, in order visited, in 'out'.
+// For example, this graph:
+// A ---> C ----.
+//  \           v
+//   `--> B --> D
+// Might result in this in 'out':
+// out[0] = D
+// out[1] = B
+// out[2] = C
+// out[3] = A
+// Note: results are undefined if there is a cycle in the graph.
+void TopologicalSort(const Graph& graph, std::vector<Vertex::Index>* out);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_GENERATOR_TOPOLOGICAL_SORT_H_
diff --git a/payload_generator/topological_sort_unittest.cc b/payload_generator/topological_sort_unittest.cc
new file mode 100644
index 0000000..1d866a7
--- /dev/null
+++ b/payload_generator/topological_sort_unittest.cc
@@ -0,0 +1,95 @@
+//
+// Copyright (C) 2010 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 "update_engine/payload_generator/topological_sort.h"
+
+#include <utility>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/payload_generator/graph_types.h"
+
+using std::make_pair;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+class TopologicalSortTest : public ::testing::Test {};
+
+namespace {
+// Returns true if the value is found in vect. If found, the index is stored
+// in out_index if out_index is not null.
+template<typename T>
+bool IndexOf(const vector<T>& vect,
+             const T& value,
+             typename vector<T>::size_type* out_index) {
+  for (typename vector<T>::size_type i = 0; i < vect.size(); i++) {
+    if (vect[i] == value) {
+      if (out_index) {
+        *out_index = i;
+      }
+      return true;
+    }
+  }
+  return false;
+}
+}  // namespace
+
+TEST(TopologicalSortTest, SimpleTest) {
+  int counter = 0;
+  const Vertex::Index n_a = counter++;
+  const Vertex::Index n_b = counter++;
+  const Vertex::Index n_c = counter++;
+  const Vertex::Index n_d = counter++;
+  const Vertex::Index n_e = counter++;
+  const Vertex::Index n_f = counter++;
+  const Vertex::Index n_g = counter++;
+  const Vertex::Index n_h = counter++;
+  const Vertex::Index n_i = counter++;
+  const Vertex::Index n_j = counter++;
+  const Graph::size_type kNodeCount = counter++;
+
+  Graph graph(kNodeCount);
+
+  graph[n_i].out_edges.insert(make_pair(n_j, EdgeProperties()));
+  graph[n_i].out_edges.insert(make_pair(n_c, EdgeProperties()));
+  graph[n_i].out_edges.insert(make_pair(n_e, EdgeProperties()));
+  graph[n_i].out_edges.insert(make_pair(n_h, EdgeProperties()));
+  graph[n_c].out_edges.insert(make_pair(n_b, EdgeProperties()));
+  graph[n_b].out_edges.insert(make_pair(n_a, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_d, EdgeProperties()));
+  graph[n_e].out_edges.insert(make_pair(n_g, EdgeProperties()));
+  graph[n_g].out_edges.insert(make_pair(n_d, EdgeProperties()));
+  graph[n_g].out_edges.insert(make_pair(n_f, EdgeProperties()));
+  graph[n_d].out_edges.insert(make_pair(n_a, EdgeProperties()));
+
+  vector<Vertex::Index> sorted;
+  TopologicalSort(graph, &sorted);
+
+  for (Vertex::Index i = 0; i < graph.size(); i++) {
+    vector<Vertex::Index>::size_type src_index = 0;
+    EXPECT_TRUE(IndexOf(sorted, i, &src_index));
+    for (Vertex::EdgeMap::const_iterator it = graph[i].out_edges.begin();
+         it != graph[i].out_edges.end(); ++it) {
+      vector<Vertex::Index>::size_type dst_index = 0;
+      EXPECT_TRUE(IndexOf(sorted, it->first, &dst_index));
+      EXPECT_LT(dst_index, src_index);
+    }
+  }
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_generator/zip_unittest.cc b/payload_generator/zip_unittest.cc
new file mode 100644
index 0000000..49b08b0
--- /dev/null
+++ b/payload_generator/zip_unittest.cc
@@ -0,0 +1,114 @@
+//
+// Copyright (C) 2011 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 <string.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <gtest/gtest.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/payload_generator/bzip.h"
+
+using chromeos_update_engine::test_utils::kRandomString;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+template <typename T>
+class ZipTest : public ::testing::Test {
+ public:
+  bool ZipDecompress(const brillo::Blob& in, brillo::Blob* out) const = 0;
+  bool ZipCompress(const brillo::Blob& in, brillo::Blob* out) const = 0;
+  bool ZipCompressString(const string& str, brillo::Blob* out) const = 0;
+  bool ZipDecompressString(const string& str, brillo::Blob* out) const = 0;
+};
+
+class BzipTest {};
+
+template <>
+class ZipTest<BzipTest> : public ::testing::Test {
+ public:
+  bool ZipDecompress(const brillo::Blob& in, brillo::Blob* out) const {
+    return BzipDecompress(in, out);
+  }
+  bool ZipCompress(const brillo::Blob& in, brillo::Blob* out) const {
+    return BzipCompress(in, out);
+  }
+  bool ZipCompressString(const string& str, brillo::Blob* out) const {
+    return BzipCompressString(str, out);
+  }
+  bool ZipDecompressString(const string& str, brillo::Blob* out) const {
+    return BzipDecompressString(str, out);
+  }
+};
+
+typedef ::testing::Types<BzipTest> ZipTestTypes;
+TYPED_TEST_CASE(ZipTest, ZipTestTypes);
+
+
+
+TYPED_TEST(ZipTest, SimpleTest) {
+  string in("this should compress well xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
+            "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
+            "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
+            "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
+            "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
+            "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx");
+  brillo::Blob out;
+  EXPECT_TRUE(this->ZipCompressString(in, &out));
+  EXPECT_LT(out.size(), in.size());
+  EXPECT_GT(out.size(), 0);
+  brillo::Blob decompressed;
+  EXPECT_TRUE(this->ZipDecompress(out, &decompressed));
+  EXPECT_EQ(in.size(), decompressed.size());
+  EXPECT_TRUE(!memcmp(in.data(), decompressed.data(), in.size()));
+}
+
+TYPED_TEST(ZipTest, PoorCompressionTest) {
+  string in(reinterpret_cast<const char*>(kRandomString),
+            sizeof(kRandomString));
+  brillo::Blob out;
+  EXPECT_TRUE(this->ZipCompressString(in, &out));
+  EXPECT_GT(out.size(), in.size());
+  string out_string(out.begin(), out.end());
+  brillo::Blob decompressed;
+  EXPECT_TRUE(this->ZipDecompressString(out_string, &decompressed));
+  EXPECT_EQ(in.size(), decompressed.size());
+  EXPECT_TRUE(!memcmp(in.data(), decompressed.data(), in.size()));
+}
+
+TYPED_TEST(ZipTest, MalformedZipTest) {
+  string in(reinterpret_cast<const char*>(kRandomString),
+            sizeof(kRandomString));
+  brillo::Blob out;
+  EXPECT_FALSE(this->ZipDecompressString(in, &out));
+}
+
+TYPED_TEST(ZipTest, EmptyInputsTest) {
+  string in;
+  brillo::Blob out;
+  EXPECT_TRUE(this->ZipDecompressString(in, &out));
+  EXPECT_EQ(0, out.size());
+
+  EXPECT_TRUE(this->ZipCompressString(in, &out));
+  EXPECT_EQ(0, out.size());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_state.cc b/payload_state.cc
new file mode 100644
index 0000000..8594f28
--- /dev/null
+++ b/payload_state.cc
@@ -0,0 +1,1382 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_state.h"
+
+#include <algorithm>
+#include <string>
+
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <metrics/metrics_library.h>
+#include <policy/device_policy.h>
+
+#include "update_engine/common/clock.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/metrics_utils.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/payload_consumer/install_plan.h"
+#include "update_engine/system_state.h"
+
+using base::Time;
+using base::TimeDelta;
+using std::min;
+using std::string;
+
+namespace chromeos_update_engine {
+
+const TimeDelta PayloadState::kDurationSlack = TimeDelta::FromSeconds(600);
+
+// We want to upperbound backoffs to 16 days
+static const int kMaxBackoffDays = 16;
+
+// We want to randomize retry attempts after the backoff by +/- 6 hours.
+static const uint32_t kMaxBackoffFuzzMinutes = 12 * 60;
+
+PayloadState::PayloadState()
+    : prefs_(nullptr),
+      using_p2p_for_downloading_(false),
+      p2p_num_attempts_(0),
+      payload_attempt_number_(0),
+      full_payload_attempt_number_(0),
+      url_index_(0),
+      url_failure_count_(0),
+      url_switch_count_(0),
+      attempt_num_bytes_downloaded_(0),
+      attempt_connection_type_(metrics::ConnectionType::kUnknown),
+      attempt_type_(AttemptType::kUpdate) {
+  for (int i = 0; i <= kNumDownloadSources; i++)
+    total_bytes_downloaded_[i] = current_bytes_downloaded_[i] = 0;
+}
+
+bool PayloadState::Initialize(SystemState* system_state) {
+  system_state_ = system_state;
+  prefs_ = system_state_->prefs();
+  powerwash_safe_prefs_ = system_state_->powerwash_safe_prefs();
+  LoadResponseSignature();
+  LoadPayloadAttemptNumber();
+  LoadFullPayloadAttemptNumber();
+  LoadUrlIndex();
+  LoadUrlFailureCount();
+  LoadUrlSwitchCount();
+  LoadBackoffExpiryTime();
+  LoadUpdateTimestampStart();
+  // The LoadUpdateDurationUptime() method relies on LoadUpdateTimestampStart()
+  // being called before it. Don't reorder.
+  LoadUpdateDurationUptime();
+  for (int i = 0; i < kNumDownloadSources; i++) {
+    DownloadSource source = static_cast<DownloadSource>(i);
+    LoadCurrentBytesDownloaded(source);
+    LoadTotalBytesDownloaded(source);
+  }
+  LoadNumReboots();
+  LoadNumResponsesSeen();
+  LoadRollbackVersion();
+  LoadP2PFirstAttemptTimestamp();
+  LoadP2PNumAttempts();
+  return true;
+}
+
+void PayloadState::SetResponse(const OmahaResponse& omaha_response) {
+  // Always store the latest response.
+  response_ = omaha_response;
+
+  // Compute the candidate URLs first as they are used to calculate the
+  // response signature so that a change in enterprise policy for
+  // HTTP downloads being enabled or not could be honored as soon as the
+  // next update check happens.
+  ComputeCandidateUrls();
+
+  // Check if the "signature" of this response (i.e. the fields we care about)
+  // has changed.
+  string new_response_signature = CalculateResponseSignature();
+  bool has_response_changed = (response_signature_ != new_response_signature);
+
+  // If the response has changed, we should persist the new signature and
+  // clear away all the existing state.
+  if (has_response_changed) {
+    LOG(INFO) << "Resetting all persisted state as this is a new response";
+    SetNumResponsesSeen(num_responses_seen_ + 1);
+    SetResponseSignature(new_response_signature);
+    ResetPersistedState();
+    return;
+  }
+
+  // This is the earliest point at which we can validate whether the URL index
+  // we loaded from the persisted state is a valid value. If the response
+  // hasn't changed but the URL index is invalid, it's indicative of some
+  // tampering of the persisted state.
+  if (static_cast<uint32_t>(url_index_) >= candidate_urls_.size()) {
+    LOG(INFO) << "Resetting all payload state as the url index seems to have "
+                 "been tampered with";
+    ResetPersistedState();
+    return;
+  }
+
+  // Update the current download source which depends on the latest value of
+  // the response.
+  UpdateCurrentDownloadSource();
+}
+
+void PayloadState::SetUsingP2PForDownloading(bool value) {
+  using_p2p_for_downloading_ = value;
+  // Update the current download source which depends on whether we are
+  // using p2p or not.
+  UpdateCurrentDownloadSource();
+}
+
+void PayloadState::DownloadComplete() {
+  LOG(INFO) << "Payload downloaded successfully";
+  IncrementPayloadAttemptNumber();
+  IncrementFullPayloadAttemptNumber();
+}
+
+void PayloadState::DownloadProgress(size_t count) {
+  if (count == 0)
+    return;
+
+  CalculateUpdateDurationUptime();
+  UpdateBytesDownloaded(count);
+
+  // We've received non-zero bytes from a recent download operation.  Since our
+  // URL failure count is meant to penalize a URL only for consecutive
+  // failures, downloading bytes successfully means we should reset the failure
+  // count (as we know at least that the URL is working). In future, we can
+  // design this to be more sophisticated to check for more intelligent failure
+  // patterns, but right now, even 1 byte downloaded will mark the URL to be
+  // good unless it hits 10 (or configured number of) consecutive failures
+  // again.
+
+  if (GetUrlFailureCount() == 0)
+    return;
+
+  LOG(INFO) << "Resetting failure count of Url" << GetUrlIndex()
+            << " to 0 as we received " << count << " bytes successfully";
+  SetUrlFailureCount(0);
+}
+
+void PayloadState::AttemptStarted(AttemptType attempt_type) {
+  // Flush previous state from abnormal attempt failure, if any.
+  ReportAndClearPersistedAttemptMetrics();
+
+  attempt_type_ = attempt_type;
+
+  ClockInterface *clock = system_state_->clock();
+  attempt_start_time_boot_ = clock->GetBootTime();
+  attempt_start_time_monotonic_ = clock->GetMonotonicTime();
+  attempt_num_bytes_downloaded_ = 0;
+
+  metrics::ConnectionType type;
+  NetworkConnectionType network_connection_type;
+  NetworkTethering tethering;
+  ConnectionManagerInterface* connection_manager =
+      system_state_->connection_manager();
+  if (!connection_manager->GetConnectionProperties(&network_connection_type,
+                                                   &tethering)) {
+    LOG(ERROR) << "Failed to determine connection type.";
+    type = metrics::ConnectionType::kUnknown;
+  } else {
+    type = metrics_utils::GetConnectionType(network_connection_type, tethering);
+  }
+  attempt_connection_type_ = type;
+
+  if (attempt_type == AttemptType::kUpdate)
+    PersistAttemptMetrics();
+}
+
+void PayloadState::UpdateResumed() {
+  LOG(INFO) << "Resuming an update that was previously started.";
+  UpdateNumReboots();
+  AttemptStarted(AttemptType::kUpdate);
+}
+
+void PayloadState::UpdateRestarted() {
+  LOG(INFO) << "Starting a new update";
+  ResetDownloadSourcesOnNewUpdate();
+  SetNumReboots(0);
+  AttemptStarted(AttemptType::kUpdate);
+}
+
+void PayloadState::UpdateSucceeded() {
+  // Send the relevant metrics that are tracked in this class to UMA.
+  CalculateUpdateDurationUptime();
+  SetUpdateTimestampEnd(system_state_->clock()->GetWallclockTime());
+
+  switch (attempt_type_) {
+    case AttemptType::kUpdate:
+      CollectAndReportAttemptMetrics(ErrorCode::kSuccess);
+      CollectAndReportSuccessfulUpdateMetrics();
+      ClearPersistedAttemptMetrics();
+      break;
+
+    case AttemptType::kRollback:
+      metrics::ReportRollbackMetrics(system_state_,
+                                     metrics::RollbackResult::kSuccess);
+      break;
+  }
+
+  // Reset the number of responses seen since it counts from the last
+  // successful update, e.g. now.
+  SetNumResponsesSeen(0);
+
+  CreateSystemUpdatedMarkerFile();
+}
+
+void PayloadState::UpdateFailed(ErrorCode error) {
+  ErrorCode base_error = utils::GetBaseErrorCode(error);
+  LOG(INFO) << "Updating payload state for error code: " << base_error
+            << " (" << utils::CodeToString(base_error) << ")";
+
+  if (candidate_urls_.size() == 0) {
+    // This means we got this error even before we got a valid Omaha response
+    // or don't have any valid candidates in the Omaha response.
+    // So we should not advance the url_index_ in such cases.
+    LOG(INFO) << "Ignoring failures until we get a valid Omaha response.";
+    return;
+  }
+
+  switch (attempt_type_) {
+    case AttemptType::kUpdate:
+      CollectAndReportAttemptMetrics(base_error);
+      ClearPersistedAttemptMetrics();
+      break;
+
+    case AttemptType::kRollback:
+      metrics::ReportRollbackMetrics(system_state_,
+                                     metrics::RollbackResult::kFailed);
+      break;
+  }
+
+  switch (base_error) {
+    // Errors which are good indicators of a problem with a particular URL or
+    // the protocol used in the URL or entities in the communication channel
+    // (e.g. proxies). We should try the next available URL in the next update
+    // check to quickly recover from these errors.
+    case ErrorCode::kPayloadHashMismatchError:
+    case ErrorCode::kPayloadSizeMismatchError:
+    case ErrorCode::kDownloadPayloadVerificationError:
+    case ErrorCode::kDownloadPayloadPubKeyVerificationError:
+    case ErrorCode::kSignedDeltaPayloadExpectedError:
+    case ErrorCode::kDownloadInvalidMetadataMagicString:
+    case ErrorCode::kDownloadSignatureMissingInManifest:
+    case ErrorCode::kDownloadManifestParseError:
+    case ErrorCode::kDownloadMetadataSignatureError:
+    case ErrorCode::kDownloadMetadataSignatureVerificationError:
+    case ErrorCode::kDownloadMetadataSignatureMismatch:
+    case ErrorCode::kDownloadOperationHashVerificationError:
+    case ErrorCode::kDownloadOperationExecutionError:
+    case ErrorCode::kDownloadOperationHashMismatch:
+    case ErrorCode::kDownloadInvalidMetadataSize:
+    case ErrorCode::kDownloadInvalidMetadataSignature:
+    case ErrorCode::kDownloadOperationHashMissingError:
+    case ErrorCode::kDownloadMetadataSignatureMissingError:
+    case ErrorCode::kPayloadMismatchedType:
+    case ErrorCode::kUnsupportedMajorPayloadVersion:
+    case ErrorCode::kUnsupportedMinorPayloadVersion:
+      IncrementUrlIndex();
+      break;
+
+    // Errors which seem to be just transient network/communication related
+    // failures and do not indicate any inherent problem with the URL itself.
+    // So, we should keep the current URL but just increment the
+    // failure count to give it more chances. This way, while we maximize our
+    // chances of downloading from the URLs that appear earlier in the response
+    // (because download from a local server URL that appears earlier in a
+    // response is preferable than downloading from the next URL which could be
+    // a internet URL and thus could be more expensive).
+
+    case ErrorCode::kError:
+    case ErrorCode::kDownloadTransferError:
+    case ErrorCode::kDownloadWriteError:
+    case ErrorCode::kDownloadStateInitializationError:
+    case ErrorCode::kOmahaErrorInHTTPResponse:  // Aggregate for HTTP errors.
+      IncrementFailureCount();
+      break;
+
+    // Errors which are not specific to a URL and hence shouldn't result in
+    // the URL being penalized. This can happen in two cases:
+    // 1. We haven't started downloading anything: These errors don't cost us
+    // anything in terms of actual payload bytes, so we should just do the
+    // regular retries at the next update check.
+    // 2. We have successfully downloaded the payload: In this case, the
+    // payload attempt number would have been incremented and would take care
+    // of the backoff at the next update check.
+    // In either case, there's no need to update URL index or failure count.
+    case ErrorCode::kOmahaRequestError:
+    case ErrorCode::kOmahaResponseHandlerError:
+    case ErrorCode::kPostinstallRunnerError:
+    case ErrorCode::kFilesystemCopierError:
+    case ErrorCode::kInstallDeviceOpenError:
+    case ErrorCode::kKernelDeviceOpenError:
+    case ErrorCode::kDownloadNewPartitionInfoError:
+    case ErrorCode::kNewRootfsVerificationError:
+    case ErrorCode::kNewKernelVerificationError:
+    case ErrorCode::kPostinstallBootedFromFirmwareB:
+    case ErrorCode::kPostinstallFirmwareRONotUpdatable:
+    case ErrorCode::kOmahaRequestEmptyResponseError:
+    case ErrorCode::kOmahaRequestXMLParseError:
+    case ErrorCode::kOmahaResponseInvalid:
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+    case ErrorCode::kPostinstallPowerwashError:
+    case ErrorCode::kUpdateCanceledByChannelChange:
+    case ErrorCode::kOmahaRequestXMLHasEntityDecl:
+    case ErrorCode::kFilesystemVerifierError:
+      LOG(INFO) << "Not incrementing URL index or failure count for this error";
+      break;
+
+    case ErrorCode::kSuccess:                            // success code
+    case ErrorCode::kUmaReportedMax:                     // not an error code
+    case ErrorCode::kOmahaRequestHTTPResponseBase:       // aggregated already
+    case ErrorCode::kDevModeFlag:                       // not an error code
+    case ErrorCode::kResumedFlag:                        // not an error code
+    case ErrorCode::kTestImageFlag:                      // not an error code
+    case ErrorCode::kTestOmahaUrlFlag:                   // not an error code
+    case ErrorCode::kSpecialFlags:                       // not an error code
+      // These shouldn't happen. Enumerating these  explicitly here so that we
+      // can let the compiler warn about new error codes that are added to
+      // action_processor.h but not added here.
+      LOG(WARNING) << "Unexpected error code for UpdateFailed";
+      break;
+
+    // Note: Not adding a default here so as to let the compiler warn us of
+    // any new enums that were added in the .h but not listed in this switch.
+  }
+}
+
+bool PayloadState::ShouldBackoffDownload() {
+  if (response_.disable_payload_backoff) {
+    LOG(INFO) << "Payload backoff logic is disabled. "
+                 "Can proceed with the download";
+    return false;
+  }
+  if (GetUsingP2PForDownloading() && !GetP2PUrl().empty()) {
+    LOG(INFO) << "Payload backoff logic is disabled because download "
+              << "will happen from local peer (via p2p).";
+    return false;
+  }
+  if (system_state_->request_params()->interactive()) {
+    LOG(INFO) << "Payload backoff disabled for interactive update checks.";
+    return false;
+  }
+  if (response_.is_delta_payload) {
+    // If delta payloads fail, we want to fallback quickly to full payloads as
+    // they are more likely to succeed. Exponential backoffs would greatly
+    // slow down the fallback to full payloads.  So we don't backoff for delta
+    // payloads.
+    LOG(INFO) << "No backoffs for delta payloads. "
+              << "Can proceed with the download";
+    return false;
+  }
+
+  if (!system_state_->hardware()->IsOfficialBuild()) {
+    // Backoffs are needed only for official builds. We do not want any delays
+    // or update failures due to backoffs during testing or development.
+    LOG(INFO) << "No backoffs for test/dev images. "
+              << "Can proceed with the download";
+    return false;
+  }
+
+  if (backoff_expiry_time_.is_null()) {
+    LOG(INFO) << "No backoff expiry time has been set. "
+              << "Can proceed with the download";
+    return false;
+  }
+
+  if (backoff_expiry_time_ < Time::Now()) {
+    LOG(INFO) << "The backoff expiry time ("
+              << utils::ToString(backoff_expiry_time_)
+              << ") has elapsed. Can proceed with the download";
+    return false;
+  }
+
+  LOG(INFO) << "Cannot proceed with downloads as we need to backoff until "
+            << utils::ToString(backoff_expiry_time_);
+  return true;
+}
+
+void PayloadState::Rollback() {
+  SetRollbackVersion(system_state_->request_params()->app_version());
+  AttemptStarted(AttemptType::kRollback);
+}
+
+void PayloadState::IncrementPayloadAttemptNumber() {
+  // Update the payload attempt number for both payload types: full and delta.
+  SetPayloadAttemptNumber(GetPayloadAttemptNumber() + 1);
+}
+
+void PayloadState::IncrementFullPayloadAttemptNumber() {
+  // Update the payload attempt number for full payloads and the backoff time.
+  if (response_.is_delta_payload) {
+    LOG(INFO) << "Not incrementing payload attempt number for delta payloads";
+    return;
+  }
+
+  LOG(INFO) << "Incrementing the full payload attempt number";
+  SetFullPayloadAttemptNumber(GetFullPayloadAttemptNumber() + 1);
+  UpdateBackoffExpiryTime();
+}
+
+void PayloadState::IncrementUrlIndex() {
+  uint32_t next_url_index = GetUrlIndex() + 1;
+  if (next_url_index < candidate_urls_.size()) {
+    LOG(INFO) << "Incrementing the URL index for next attempt";
+    SetUrlIndex(next_url_index);
+  } else {
+    LOG(INFO) << "Resetting the current URL index (" << GetUrlIndex() << ") to "
+              << "0 as we only have " << candidate_urls_.size()
+              << " candidate URL(s)";
+    SetUrlIndex(0);
+    IncrementPayloadAttemptNumber();
+    IncrementFullPayloadAttemptNumber();
+  }
+
+  // If we have multiple URLs, record that we just switched to another one
+  if (candidate_urls_.size() > 1)
+    SetUrlSwitchCount(url_switch_count_ + 1);
+
+  // Whenever we update the URL index, we should also clear the URL failure
+  // count so we can start over fresh for the new URL.
+  SetUrlFailureCount(0);
+}
+
+void PayloadState::IncrementFailureCount() {
+  uint32_t next_url_failure_count = GetUrlFailureCount() + 1;
+  if (next_url_failure_count < response_.max_failure_count_per_url) {
+    LOG(INFO) << "Incrementing the URL failure count";
+    SetUrlFailureCount(next_url_failure_count);
+  } else {
+    LOG(INFO) << "Reached max number of failures for Url" << GetUrlIndex()
+              << ". Trying next available URL";
+    IncrementUrlIndex();
+  }
+}
+
+void PayloadState::UpdateBackoffExpiryTime() {
+  if (response_.disable_payload_backoff) {
+    LOG(INFO) << "Resetting backoff expiry time as payload backoff is disabled";
+    SetBackoffExpiryTime(Time());
+    return;
+  }
+
+  if (GetFullPayloadAttemptNumber() == 0) {
+    SetBackoffExpiryTime(Time());
+    return;
+  }
+
+  // Since we're doing left-shift below, make sure we don't shift more
+  // than this. E.g. if int is 4-bytes, don't left-shift more than 30 bits,
+  // since we don't expect value of kMaxBackoffDays to be more than 100 anyway.
+  int num_days = 1;  // the value to be shifted.
+  const int kMaxShifts = (sizeof(num_days) * 8) - 2;
+
+  // Normal backoff days is 2 raised to (payload_attempt_number - 1).
+  // E.g. if payload_attempt_number is over 30, limit power to 30.
+  int power = min(GetFullPayloadAttemptNumber() - 1, kMaxShifts);
+
+  // The number of days is the minimum of 2 raised to (payload_attempt_number
+  // - 1) or kMaxBackoffDays.
+  num_days = min(num_days << power, kMaxBackoffDays);
+
+  // We don't want all retries to happen exactly at the same time when
+  // retrying after backoff. So add some random minutes to fuzz.
+  int fuzz_minutes = utils::FuzzInt(0, kMaxBackoffFuzzMinutes);
+  TimeDelta next_backoff_interval = TimeDelta::FromDays(num_days) +
+                                    TimeDelta::FromMinutes(fuzz_minutes);
+  LOG(INFO) << "Incrementing the backoff expiry time by "
+            << utils::FormatTimeDelta(next_backoff_interval);
+  SetBackoffExpiryTime(Time::Now() + next_backoff_interval);
+}
+
+void PayloadState::UpdateCurrentDownloadSource() {
+  current_download_source_ = kNumDownloadSources;
+
+  if (using_p2p_for_downloading_) {
+    current_download_source_ = kDownloadSourceHttpPeer;
+  } else if (GetUrlIndex() < candidate_urls_.size())  {
+    string current_url = candidate_urls_[GetUrlIndex()];
+    if (base::StartsWithASCII(current_url, "https://", false))
+      current_download_source_ = kDownloadSourceHttpsServer;
+    else if (base::StartsWithASCII(current_url, "http://", false))
+      current_download_source_ = kDownloadSourceHttpServer;
+  }
+
+  LOG(INFO) << "Current download source: "
+            << utils::ToString(current_download_source_);
+}
+
+void PayloadState::UpdateBytesDownloaded(size_t count) {
+  SetCurrentBytesDownloaded(
+      current_download_source_,
+      GetCurrentBytesDownloaded(current_download_source_) + count,
+      false);
+  SetTotalBytesDownloaded(
+      current_download_source_,
+      GetTotalBytesDownloaded(current_download_source_) + count,
+      false);
+
+  attempt_num_bytes_downloaded_ += count;
+}
+
+PayloadType PayloadState::CalculatePayloadType() {
+  PayloadType payload_type;
+  OmahaRequestParams* params = system_state_->request_params();
+  if (response_.is_delta_payload) {
+    payload_type = kPayloadTypeDelta;
+  } else if (params->delta_okay()) {
+    payload_type = kPayloadTypeFull;
+  } else {  // Full payload, delta was not allowed by request.
+    payload_type = kPayloadTypeForcedFull;
+  }
+  return payload_type;
+}
+
+// TODO(zeuthen): Currently we don't report the UpdateEngine.Attempt.*
+// metrics if the attempt ends abnormally, e.g. if the update_engine
+// process crashes or the device is rebooted. See
+// http://crbug.com/357676
+void PayloadState::CollectAndReportAttemptMetrics(ErrorCode code) {
+  int attempt_number = GetPayloadAttemptNumber();
+
+  PayloadType payload_type = CalculatePayloadType();
+
+  int64_t payload_size = response_.size;
+
+  int64_t payload_bytes_downloaded = attempt_num_bytes_downloaded_;
+
+  ClockInterface *clock = system_state_->clock();
+  TimeDelta duration = clock->GetBootTime() - attempt_start_time_boot_;
+  TimeDelta duration_uptime = clock->GetMonotonicTime() -
+      attempt_start_time_monotonic_;
+
+  int64_t payload_download_speed_bps = 0;
+  int64_t usec = duration_uptime.InMicroseconds();
+  if (usec > 0) {
+    double sec = static_cast<double>(usec) / Time::kMicrosecondsPerSecond;
+    double bps = static_cast<double>(payload_bytes_downloaded) / sec;
+    payload_download_speed_bps = static_cast<int64_t>(bps);
+  }
+
+  DownloadSource download_source = current_download_source_;
+
+  metrics::DownloadErrorCode payload_download_error_code =
+    metrics::DownloadErrorCode::kUnset;
+  ErrorCode internal_error_code = ErrorCode::kSuccess;
+  metrics::AttemptResult attempt_result = metrics_utils::GetAttemptResult(code);
+
+  // Add additional detail to AttemptResult
+  switch (attempt_result) {
+    case metrics::AttemptResult::kPayloadDownloadError:
+      payload_download_error_code = metrics_utils::GetDownloadErrorCode(code);
+      break;
+
+    case metrics::AttemptResult::kInternalError:
+      internal_error_code = code;
+      break;
+
+    // Explicit fall-through for cases where we do not have additional
+    // detail. We avoid the default keyword to force people adding new
+    // AttemptResult values to visit this code and examine whether
+    // additional detail is needed.
+    case metrics::AttemptResult::kUpdateSucceeded:
+    case metrics::AttemptResult::kMetadataMalformed:
+    case metrics::AttemptResult::kOperationMalformed:
+    case metrics::AttemptResult::kOperationExecutionError:
+    case metrics::AttemptResult::kMetadataVerificationFailed:
+    case metrics::AttemptResult::kPayloadVerificationFailed:
+    case metrics::AttemptResult::kVerificationFailed:
+    case metrics::AttemptResult::kPostInstallFailed:
+    case metrics::AttemptResult::kAbnormalTermination:
+    case metrics::AttemptResult::kNumConstants:
+    case metrics::AttemptResult::kUnset:
+      break;
+  }
+
+  metrics::ReportUpdateAttemptMetrics(system_state_,
+                                      attempt_number,
+                                      payload_type,
+                                      duration,
+                                      duration_uptime,
+                                      payload_size,
+                                      payload_bytes_downloaded,
+                                      payload_download_speed_bps,
+                                      download_source,
+                                      attempt_result,
+                                      internal_error_code,
+                                      payload_download_error_code,
+                                      attempt_connection_type_);
+}
+
+void PayloadState::PersistAttemptMetrics() {
+  // TODO(zeuthen): For now we only persist whether an attempt was in
+  // progress and not values/metrics related to the attempt. This
+  // means that when this happens, of all the UpdateEngine.Attempt.*
+  // metrics, only UpdateEngine.Attempt.Result is reported (with the
+  // value |kAbnormalTermination|). In the future we might want to
+  // persist more data so we can report other metrics in the
+  // UpdateEngine.Attempt.* namespace when this happens.
+  prefs_->SetBoolean(kPrefsAttemptInProgress, true);
+}
+
+void PayloadState::ClearPersistedAttemptMetrics() {
+  prefs_->Delete(kPrefsAttemptInProgress);
+}
+
+void PayloadState::ReportAndClearPersistedAttemptMetrics() {
+  bool attempt_in_progress = false;
+  if (!prefs_->GetBoolean(kPrefsAttemptInProgress, &attempt_in_progress))
+    return;
+  if (!attempt_in_progress)
+    return;
+
+  metrics::ReportAbnormallyTerminatedUpdateAttemptMetrics(system_state_);
+
+  ClearPersistedAttemptMetrics();
+}
+
+void PayloadState::CollectAndReportSuccessfulUpdateMetrics() {
+  string metric;
+
+  // Report metrics collected from all known download sources to UMA.
+  int64_t total_bytes_by_source[kNumDownloadSources];
+  int64_t successful_bytes = 0;
+  int64_t total_bytes = 0;
+  int64_t successful_mbs = 0;
+  int64_t total_mbs = 0;
+
+  for (int i = 0; i < kNumDownloadSources; i++) {
+    DownloadSource source = static_cast<DownloadSource>(i);
+    int64_t bytes;
+
+    // Only consider this download source (and send byte counts) as
+    // having been used if we downloaded a non-trivial amount of bytes
+    // (e.g. at least 1 MiB) that contributed to the final success of
+    // the update. Otherwise we're going to end up with a lot of
+    // zero-byte events in the histogram.
+
+    bytes = GetCurrentBytesDownloaded(source);
+    successful_bytes += bytes;
+    successful_mbs += bytes / kNumBytesInOneMiB;
+    SetCurrentBytesDownloaded(source, 0, true);
+
+    bytes = GetTotalBytesDownloaded(source);
+    total_bytes_by_source[i] = bytes;
+    total_bytes += bytes;
+    total_mbs += bytes / kNumBytesInOneMiB;
+    SetTotalBytesDownloaded(source, 0, true);
+  }
+
+  int download_overhead_percentage = 0;
+  if (successful_bytes > 0) {
+    download_overhead_percentage = (total_bytes - successful_bytes) * 100ULL /
+                                   successful_bytes;
+  }
+
+  int url_switch_count = static_cast<int>(url_switch_count_);
+
+  int reboot_count = GetNumReboots();
+
+  SetNumReboots(0);
+
+  TimeDelta duration = GetUpdateDuration();
+
+  prefs_->Delete(kPrefsUpdateTimestampStart);
+  prefs_->Delete(kPrefsUpdateDurationUptime);
+
+  PayloadType payload_type = CalculatePayloadType();
+
+  int64_t payload_size = response_.size;
+
+  int attempt_count = GetPayloadAttemptNumber();
+
+  int updates_abandoned_count = num_responses_seen_ - 1;
+
+  metrics::ReportSuccessfulUpdateMetrics(system_state_,
+                                         attempt_count,
+                                         updates_abandoned_count,
+                                         payload_type,
+                                         payload_size,
+                                         total_bytes_by_source,
+                                         download_overhead_percentage,
+                                         duration,
+                                         reboot_count,
+                                         url_switch_count);
+}
+
+void PayloadState::UpdateNumReboots() {
+  // We only update the reboot count when the system has been detected to have
+  // been rebooted.
+  if (!system_state_->system_rebooted()) {
+    return;
+  }
+
+  SetNumReboots(GetNumReboots() + 1);
+}
+
+void PayloadState::SetNumReboots(uint32_t num_reboots) {
+  CHECK(prefs_);
+  num_reboots_ = num_reboots;
+  prefs_->SetInt64(kPrefsNumReboots, num_reboots);
+  LOG(INFO) << "Number of Reboots during current update attempt = "
+            << num_reboots_;
+}
+
+void PayloadState::ResetPersistedState() {
+  SetPayloadAttemptNumber(0);
+  SetFullPayloadAttemptNumber(0);
+  SetUrlIndex(0);
+  SetUrlFailureCount(0);
+  SetUrlSwitchCount(0);
+  UpdateBackoffExpiryTime();  // This will reset the backoff expiry time.
+  SetUpdateTimestampStart(system_state_->clock()->GetWallclockTime());
+  SetUpdateTimestampEnd(Time());  // Set to null time
+  SetUpdateDurationUptime(TimeDelta::FromSeconds(0));
+  ResetDownloadSourcesOnNewUpdate();
+  ResetRollbackVersion();
+  SetP2PNumAttempts(0);
+  SetP2PFirstAttemptTimestamp(Time());  // Set to null time
+  SetScatteringWaitPeriod(TimeDelta());
+}
+
+void PayloadState::ResetRollbackVersion() {
+  CHECK(powerwash_safe_prefs_);
+  rollback_version_ = "";
+  powerwash_safe_prefs_->Delete(kPrefsRollbackVersion);
+}
+
+void PayloadState::ResetDownloadSourcesOnNewUpdate() {
+  for (int i = 0; i < kNumDownloadSources; i++) {
+    DownloadSource source = static_cast<DownloadSource>(i);
+    SetCurrentBytesDownloaded(source, 0, true);
+    // Note: Not resetting the TotalBytesDownloaded as we want that metric
+    // to count the bytes downloaded across various update attempts until
+    // we have successfully applied the update.
+  }
+}
+
+int64_t PayloadState::GetPersistedValue(const string& key) {
+  CHECK(prefs_);
+  if (!prefs_->Exists(key))
+    return 0;
+
+  int64_t stored_value;
+  if (!prefs_->GetInt64(key, &stored_value))
+    return 0;
+
+  if (stored_value < 0) {
+    LOG(ERROR) << key << ": Invalid value (" << stored_value
+               << ") in persisted state. Defaulting to 0";
+    return 0;
+  }
+
+  return stored_value;
+}
+
+string PayloadState::CalculateResponseSignature() {
+  string response_sign = base::StringPrintf(
+      "NumURLs = %d\n", static_cast<int>(candidate_urls_.size()));
+
+  for (size_t i = 0; i < candidate_urls_.size(); i++)
+    response_sign += base::StringPrintf("Candidate Url%d = %s\n",
+                                        static_cast<int>(i),
+                                        candidate_urls_[i].c_str());
+
+  response_sign += base::StringPrintf(
+      "Payload Size = %ju\n"
+      "Payload Sha256 Hash = %s\n"
+      "Metadata Size = %ju\n"
+      "Metadata Signature = %s\n"
+      "Is Delta Payload = %d\n"
+      "Max Failure Count Per Url = %d\n"
+      "Disable Payload Backoff = %d\n",
+      static_cast<uintmax_t>(response_.size),
+      response_.hash.c_str(),
+      static_cast<uintmax_t>(response_.metadata_size),
+      response_.metadata_signature.c_str(),
+      response_.is_delta_payload,
+      response_.max_failure_count_per_url,
+      response_.disable_payload_backoff);
+  return response_sign;
+}
+
+void PayloadState::LoadResponseSignature() {
+  CHECK(prefs_);
+  string stored_value;
+  if (prefs_->Exists(kPrefsCurrentResponseSignature) &&
+      prefs_->GetString(kPrefsCurrentResponseSignature, &stored_value)) {
+    SetResponseSignature(stored_value);
+  }
+}
+
+void PayloadState::SetResponseSignature(const string& response_signature) {
+  CHECK(prefs_);
+  response_signature_ = response_signature;
+  LOG(INFO) << "Current Response Signature = \n" << response_signature_;
+  prefs_->SetString(kPrefsCurrentResponseSignature, response_signature_);
+}
+
+void PayloadState::LoadPayloadAttemptNumber() {
+  SetPayloadAttemptNumber(GetPersistedValue(kPrefsPayloadAttemptNumber));
+}
+
+void PayloadState::LoadFullPayloadAttemptNumber() {
+  SetFullPayloadAttemptNumber(GetPersistedValue(
+      kPrefsFullPayloadAttemptNumber));
+}
+
+void PayloadState::SetPayloadAttemptNumber(int payload_attempt_number) {
+  CHECK(prefs_);
+  payload_attempt_number_ = payload_attempt_number;
+  LOG(INFO) << "Payload Attempt Number = " << payload_attempt_number_;
+  prefs_->SetInt64(kPrefsPayloadAttemptNumber, payload_attempt_number_);
+}
+
+void PayloadState::SetFullPayloadAttemptNumber(
+    int full_payload_attempt_number) {
+  CHECK(prefs_);
+  full_payload_attempt_number_ = full_payload_attempt_number;
+  LOG(INFO) << "Full Payload Attempt Number = " << full_payload_attempt_number_;
+  prefs_->SetInt64(kPrefsFullPayloadAttemptNumber,
+      full_payload_attempt_number_);
+}
+
+void PayloadState::LoadUrlIndex() {
+  SetUrlIndex(GetPersistedValue(kPrefsCurrentUrlIndex));
+}
+
+void PayloadState::SetUrlIndex(uint32_t url_index) {
+  CHECK(prefs_);
+  url_index_ = url_index;
+  LOG(INFO) << "Current URL Index = " << url_index_;
+  prefs_->SetInt64(kPrefsCurrentUrlIndex, url_index_);
+
+  // Also update the download source, which is purely dependent on the
+  // current URL index alone.
+  UpdateCurrentDownloadSource();
+}
+
+void PayloadState::LoadScatteringWaitPeriod() {
+  SetScatteringWaitPeriod(
+      TimeDelta::FromSeconds(GetPersistedValue(kPrefsWallClockWaitPeriod)));
+}
+
+void PayloadState::SetScatteringWaitPeriod(TimeDelta wait_period) {
+  CHECK(prefs_);
+  scattering_wait_period_ = wait_period;
+  LOG(INFO) << "Scattering Wait Period (seconds) = "
+            << scattering_wait_period_.InSeconds();
+  if (scattering_wait_period_.InSeconds() > 0) {
+    prefs_->SetInt64(kPrefsWallClockWaitPeriod,
+                     scattering_wait_period_.InSeconds());
+  } else {
+    prefs_->Delete(kPrefsWallClockWaitPeriod);
+  }
+}
+
+void PayloadState::LoadUrlSwitchCount() {
+  SetUrlSwitchCount(GetPersistedValue(kPrefsUrlSwitchCount));
+}
+
+void PayloadState::SetUrlSwitchCount(uint32_t url_switch_count) {
+  CHECK(prefs_);
+  url_switch_count_ = url_switch_count;
+  LOG(INFO) << "URL Switch Count = " << url_switch_count_;
+  prefs_->SetInt64(kPrefsUrlSwitchCount, url_switch_count_);
+}
+
+void PayloadState::LoadUrlFailureCount() {
+  SetUrlFailureCount(GetPersistedValue(kPrefsCurrentUrlFailureCount));
+}
+
+void PayloadState::SetUrlFailureCount(uint32_t url_failure_count) {
+  CHECK(prefs_);
+  url_failure_count_ = url_failure_count;
+  LOG(INFO) << "Current URL (Url" << GetUrlIndex()
+            << ")'s Failure Count = " << url_failure_count_;
+  prefs_->SetInt64(kPrefsCurrentUrlFailureCount, url_failure_count_);
+}
+
+void PayloadState::LoadBackoffExpiryTime() {
+  CHECK(prefs_);
+  int64_t stored_value;
+  if (!prefs_->Exists(kPrefsBackoffExpiryTime))
+    return;
+
+  if (!prefs_->GetInt64(kPrefsBackoffExpiryTime, &stored_value))
+    return;
+
+  Time stored_time = Time::FromInternalValue(stored_value);
+  if (stored_time > Time::Now() + TimeDelta::FromDays(kMaxBackoffDays)) {
+    LOG(ERROR) << "Invalid backoff expiry time ("
+               << utils::ToString(stored_time)
+               << ") in persisted state. Resetting.";
+    stored_time = Time();
+  }
+  SetBackoffExpiryTime(stored_time);
+}
+
+void PayloadState::SetBackoffExpiryTime(const Time& new_time) {
+  CHECK(prefs_);
+  backoff_expiry_time_ = new_time;
+  LOG(INFO) << "Backoff Expiry Time = "
+            << utils::ToString(backoff_expiry_time_);
+  prefs_->SetInt64(kPrefsBackoffExpiryTime,
+                   backoff_expiry_time_.ToInternalValue());
+}
+
+TimeDelta PayloadState::GetUpdateDuration() {
+  Time end_time = update_timestamp_end_.is_null()
+    ? system_state_->clock()->GetWallclockTime() :
+      update_timestamp_end_;
+  return end_time - update_timestamp_start_;
+}
+
+void PayloadState::LoadUpdateTimestampStart() {
+  int64_t stored_value;
+  Time stored_time;
+
+  CHECK(prefs_);
+
+  Time now = system_state_->clock()->GetWallclockTime();
+
+  if (!prefs_->Exists(kPrefsUpdateTimestampStart)) {
+    // The preference missing is not unexpected - in that case, just
+    // use the current time as start time
+    stored_time = now;
+  } else if (!prefs_->GetInt64(kPrefsUpdateTimestampStart, &stored_value)) {
+    LOG(ERROR) << "Invalid UpdateTimestampStart value. Resetting.";
+    stored_time = now;
+  } else {
+    stored_time = Time::FromInternalValue(stored_value);
+  }
+
+  // Sanity check: If the time read from disk is in the future
+  // (modulo some slack to account for possible NTP drift
+  // adjustments), something is fishy and we should report and
+  // reset.
+  TimeDelta duration_according_to_stored_time = now - stored_time;
+  if (duration_according_to_stored_time < -kDurationSlack) {
+    LOG(ERROR) << "The UpdateTimestampStart value ("
+               << utils::ToString(stored_time)
+               << ") in persisted state is "
+               << utils::FormatTimeDelta(duration_according_to_stored_time)
+               << " in the future. Resetting.";
+    stored_time = now;
+  }
+
+  SetUpdateTimestampStart(stored_time);
+}
+
+void PayloadState::SetUpdateTimestampStart(const Time& value) {
+  CHECK(prefs_);
+  update_timestamp_start_ = value;
+  prefs_->SetInt64(kPrefsUpdateTimestampStart,
+                   update_timestamp_start_.ToInternalValue());
+  LOG(INFO) << "Update Timestamp Start = "
+            << utils::ToString(update_timestamp_start_);
+}
+
+void PayloadState::SetUpdateTimestampEnd(const Time& value) {
+  update_timestamp_end_ = value;
+  LOG(INFO) << "Update Timestamp End = "
+            << utils::ToString(update_timestamp_end_);
+}
+
+TimeDelta PayloadState::GetUpdateDurationUptime() {
+  return update_duration_uptime_;
+}
+
+void PayloadState::LoadUpdateDurationUptime() {
+  int64_t stored_value;
+  TimeDelta stored_delta;
+
+  CHECK(prefs_);
+
+  if (!prefs_->Exists(kPrefsUpdateDurationUptime)) {
+    // The preference missing is not unexpected - in that case, just
+    // we'll use zero as the delta
+  } else if (!prefs_->GetInt64(kPrefsUpdateDurationUptime, &stored_value)) {
+    LOG(ERROR) << "Invalid UpdateDurationUptime value. Resetting.";
+    stored_delta = TimeDelta::FromSeconds(0);
+  } else {
+    stored_delta = TimeDelta::FromInternalValue(stored_value);
+  }
+
+  // Sanity-check: Uptime can never be greater than the wall-clock
+  // difference (modulo some slack). If it is, report and reset
+  // to the wall-clock difference.
+  TimeDelta diff = GetUpdateDuration() - stored_delta;
+  if (diff < -kDurationSlack) {
+    LOG(ERROR) << "The UpdateDurationUptime value ("
+               << utils::FormatTimeDelta(stored_delta)
+               << ") in persisted state is "
+               << utils::FormatTimeDelta(diff)
+               << " larger than the wall-clock delta. Resetting.";
+    stored_delta = update_duration_current_;
+  }
+
+  SetUpdateDurationUptime(stored_delta);
+}
+
+void PayloadState::LoadNumReboots() {
+  SetNumReboots(GetPersistedValue(kPrefsNumReboots));
+}
+
+void PayloadState::LoadRollbackVersion() {
+  CHECK(powerwash_safe_prefs_);
+  string rollback_version;
+  if (powerwash_safe_prefs_->GetString(kPrefsRollbackVersion,
+                                       &rollback_version)) {
+    SetRollbackVersion(rollback_version);
+  }
+}
+
+void PayloadState::SetRollbackVersion(const string& rollback_version) {
+  CHECK(powerwash_safe_prefs_);
+  LOG(INFO) << "Blacklisting version "<< rollback_version;
+  rollback_version_ = rollback_version;
+  powerwash_safe_prefs_->SetString(kPrefsRollbackVersion, rollback_version);
+}
+
+void PayloadState::SetUpdateDurationUptimeExtended(const TimeDelta& value,
+                                                   const Time& timestamp,
+                                                   bool use_logging) {
+  CHECK(prefs_);
+  update_duration_uptime_ = value;
+  update_duration_uptime_timestamp_ = timestamp;
+  prefs_->SetInt64(kPrefsUpdateDurationUptime,
+                   update_duration_uptime_.ToInternalValue());
+  if (use_logging) {
+    LOG(INFO) << "Update Duration Uptime = "
+              << utils::FormatTimeDelta(update_duration_uptime_);
+  }
+}
+
+void PayloadState::SetUpdateDurationUptime(const TimeDelta& value) {
+  Time now = system_state_->clock()->GetMonotonicTime();
+  SetUpdateDurationUptimeExtended(value, now, true);
+}
+
+void PayloadState::CalculateUpdateDurationUptime() {
+  Time now = system_state_->clock()->GetMonotonicTime();
+  TimeDelta uptime_since_last_update = now - update_duration_uptime_timestamp_;
+  TimeDelta new_uptime = update_duration_uptime_ + uptime_since_last_update;
+  // We're frequently called so avoid logging this write
+  SetUpdateDurationUptimeExtended(new_uptime, now, false);
+}
+
+string PayloadState::GetPrefsKey(const string& prefix, DownloadSource source) {
+  return prefix + "-from-" + utils::ToString(source);
+}
+
+void PayloadState::LoadCurrentBytesDownloaded(DownloadSource source) {
+  string key = GetPrefsKey(kPrefsCurrentBytesDownloaded, source);
+  SetCurrentBytesDownloaded(source, GetPersistedValue(key), true);
+}
+
+void PayloadState::SetCurrentBytesDownloaded(
+    DownloadSource source,
+    uint64_t current_bytes_downloaded,
+    bool log) {
+  CHECK(prefs_);
+
+  if (source >= kNumDownloadSources)
+    return;
+
+  // Update the in-memory value.
+  current_bytes_downloaded_[source] = current_bytes_downloaded;
+
+  string prefs_key = GetPrefsKey(kPrefsCurrentBytesDownloaded, source);
+  prefs_->SetInt64(prefs_key, current_bytes_downloaded);
+  LOG_IF(INFO, log) << "Current bytes downloaded for "
+                    << utils::ToString(source) << " = "
+                    << GetCurrentBytesDownloaded(source);
+}
+
+void PayloadState::LoadTotalBytesDownloaded(DownloadSource source) {
+  string key = GetPrefsKey(kPrefsTotalBytesDownloaded, source);
+  SetTotalBytesDownloaded(source, GetPersistedValue(key), true);
+}
+
+void PayloadState::SetTotalBytesDownloaded(
+    DownloadSource source,
+    uint64_t total_bytes_downloaded,
+    bool log) {
+  CHECK(prefs_);
+
+  if (source >= kNumDownloadSources)
+    return;
+
+  // Update the in-memory value.
+  total_bytes_downloaded_[source] = total_bytes_downloaded;
+
+  // Persist.
+  string prefs_key = GetPrefsKey(kPrefsTotalBytesDownloaded, source);
+  prefs_->SetInt64(prefs_key, total_bytes_downloaded);
+  LOG_IF(INFO, log) << "Total bytes downloaded for "
+                    << utils::ToString(source) << " = "
+                    << GetTotalBytesDownloaded(source);
+}
+
+void PayloadState::LoadNumResponsesSeen() {
+  SetNumResponsesSeen(GetPersistedValue(kPrefsNumResponsesSeen));
+}
+
+void PayloadState::SetNumResponsesSeen(int num_responses_seen) {
+  CHECK(prefs_);
+  num_responses_seen_ = num_responses_seen;
+  LOG(INFO) << "Num Responses Seen = " << num_responses_seen_;
+  prefs_->SetInt64(kPrefsNumResponsesSeen, num_responses_seen_);
+}
+
+void PayloadState::ComputeCandidateUrls() {
+  bool http_url_ok = true;
+
+  if (system_state_->hardware()->IsOfficialBuild()) {
+    const policy::DevicePolicy* policy = system_state_->device_policy();
+    if (policy && policy->GetHttpDownloadsEnabled(&http_url_ok) && !http_url_ok)
+      LOG(INFO) << "Downloads via HTTP Url are not enabled by device policy";
+  } else {
+    LOG(INFO) << "Allowing HTTP downloads for unofficial builds";
+    http_url_ok = true;
+  }
+
+  candidate_urls_.clear();
+  for (size_t i = 0; i < response_.payload_urls.size(); i++) {
+    string candidate_url = response_.payload_urls[i];
+    if (base::StartsWithASCII(candidate_url, "http://", false) && !http_url_ok)
+      continue;
+    candidate_urls_.push_back(candidate_url);
+    LOG(INFO) << "Candidate Url" << (candidate_urls_.size() - 1)
+              << ": " << candidate_url;
+  }
+
+  LOG(INFO) << "Found " << candidate_urls_.size() << " candidate URLs "
+            << "out of " << response_.payload_urls.size() << " URLs supplied";
+}
+
+void PayloadState::CreateSystemUpdatedMarkerFile() {
+  CHECK(prefs_);
+  int64_t value = system_state_->clock()->GetWallclockTime().ToInternalValue();
+  prefs_->SetInt64(kPrefsSystemUpdatedMarker, value);
+}
+
+void PayloadState::BootedIntoUpdate(TimeDelta time_to_reboot) {
+  // Send |time_to_reboot| as a UMA stat.
+  string metric = metrics::kMetricTimeToRebootMinutes;
+  system_state_->metrics_lib()->SendToUMA(metric,
+                                          time_to_reboot.InMinutes(),
+                                          0,         // min: 0 minute
+                                          30*24*60,  // max: 1 month (approx)
+                                          kNumDefaultUmaBuckets);
+  LOG(INFO) << "Uploading " << utils::FormatTimeDelta(time_to_reboot)
+            << " for metric " <<  metric;
+}
+
+void PayloadState::UpdateEngineStarted() {
+  // Flush previous state from abnormal attempt failure, if any.
+  ReportAndClearPersistedAttemptMetrics();
+
+  // Avoid the UpdateEngineStarted actions if this is not the first time we
+  // run the update engine since reboot.
+  if (!system_state_->system_rebooted())
+    return;
+
+  // Figure out if we just booted into a new update
+  if (prefs_->Exists(kPrefsSystemUpdatedMarker)) {
+    int64_t stored_value;
+    if (prefs_->GetInt64(kPrefsSystemUpdatedMarker, &stored_value)) {
+      Time system_updated_at = Time::FromInternalValue(stored_value);
+      if (!system_updated_at.is_null()) {
+        TimeDelta time_to_reboot =
+            system_state_->clock()->GetWallclockTime() - system_updated_at;
+        if (time_to_reboot.ToInternalValue() < 0) {
+          LOG(ERROR) << "time_to_reboot is negative - system_updated_at: "
+                     << utils::ToString(system_updated_at);
+        } else {
+          BootedIntoUpdate(time_to_reboot);
+        }
+      }
+    }
+    prefs_->Delete(kPrefsSystemUpdatedMarker);
+  }
+  // Check if it is needed to send metrics about a failed reboot into a new
+  // version.
+  ReportFailedBootIfNeeded();
+}
+
+void PayloadState::ReportFailedBootIfNeeded() {
+  // If the kPrefsTargetVersionInstalledFrom is present, a successfully applied
+  // payload was marked as ready immediately before the last reboot, and we
+  // need to check if such payload successfully rebooted or not.
+  if (prefs_->Exists(kPrefsTargetVersionInstalledFrom)) {
+    int64_t installed_from = 0;
+    if (!prefs_->GetInt64(kPrefsTargetVersionInstalledFrom, &installed_from)) {
+      LOG(ERROR) << "Error reading TargetVersionInstalledFrom on reboot.";
+      return;
+    }
+    // Old Chrome OS devices will write 2 or 4 in this setting, with the
+    // partition number. We are now using slot numbers (0 or 1) instead, so
+    // the following comparison will not match if we are comparing an old
+    // partition number against a new slot number, which is the correct outcome
+    // since we successfully booted the new update in that case. If the boot
+    // failed, we will read this value from the same version, so it will always
+    // be compatible.
+    if (installed_from == system_state_->boot_control()->GetCurrentSlot()) {
+      // A reboot was pending, but the chromebook is again in the same
+      // BootDevice where the update was installed from.
+      int64_t target_attempt;
+      if (!prefs_->GetInt64(kPrefsTargetVersionAttempt, &target_attempt)) {
+        LOG(ERROR) << "Error reading TargetVersionAttempt when "
+                      "TargetVersionInstalledFrom was present.";
+        target_attempt = 1;
+      }
+
+      // Report the UMA metric of the current boot failure.
+      string metric = metrics::kMetricFailedUpdateCount;
+      LOG(INFO) << "Uploading " << target_attempt
+                << " (count) for metric " <<  metric;
+      system_state_->metrics_lib()->SendToUMA(
+           metric,
+           target_attempt,
+           1,    // min value
+           50,   // max value
+           kNumDefaultUmaBuckets);
+    } else {
+      prefs_->Delete(kPrefsTargetVersionAttempt);
+      prefs_->Delete(kPrefsTargetVersionUniqueId);
+    }
+    prefs_->Delete(kPrefsTargetVersionInstalledFrom);
+  }
+}
+
+void PayloadState::ExpectRebootInNewVersion(const string& target_version_uid) {
+  // Expect to boot into the new partition in the next reboot setting the
+  // TargetVersion* flags in the Prefs.
+  string stored_target_version_uid;
+  string target_version_id;
+  string target_partition;
+  int64_t target_attempt;
+
+  if (prefs_->Exists(kPrefsTargetVersionUniqueId) &&
+      prefs_->GetString(kPrefsTargetVersionUniqueId,
+                        &stored_target_version_uid) &&
+      stored_target_version_uid == target_version_uid) {
+    if (!prefs_->GetInt64(kPrefsTargetVersionAttempt, &target_attempt))
+      target_attempt = 0;
+  } else {
+    prefs_->SetString(kPrefsTargetVersionUniqueId, target_version_uid);
+    target_attempt = 0;
+  }
+  prefs_->SetInt64(kPrefsTargetVersionAttempt, target_attempt + 1);
+
+  prefs_->SetInt64(kPrefsTargetVersionInstalledFrom,
+                   system_state_->boot_control()->GetCurrentSlot());
+}
+
+void PayloadState::ResetUpdateStatus() {
+  // Remove the TargetVersionInstalledFrom pref so that if the machine is
+  // rebooted the next boot is not flagged as failed to rebooted into the
+  // new applied payload.
+  prefs_->Delete(kPrefsTargetVersionInstalledFrom);
+
+  // Also decrement the attempt number if it exists.
+  int64_t target_attempt;
+  if (prefs_->GetInt64(kPrefsTargetVersionAttempt, &target_attempt))
+    prefs_->SetInt64(kPrefsTargetVersionAttempt, target_attempt - 1);
+}
+
+int PayloadState::GetP2PNumAttempts() {
+  return p2p_num_attempts_;
+}
+
+void PayloadState::SetP2PNumAttempts(int value) {
+  p2p_num_attempts_ = value;
+  LOG(INFO) << "p2p Num Attempts = " << p2p_num_attempts_;
+  CHECK(prefs_);
+  prefs_->SetInt64(kPrefsP2PNumAttempts, value);
+}
+
+void PayloadState::LoadP2PNumAttempts() {
+  SetP2PNumAttempts(GetPersistedValue(kPrefsP2PNumAttempts));
+}
+
+Time PayloadState::GetP2PFirstAttemptTimestamp() {
+  return p2p_first_attempt_timestamp_;
+}
+
+void PayloadState::SetP2PFirstAttemptTimestamp(const Time& time) {
+  p2p_first_attempt_timestamp_ = time;
+  LOG(INFO) << "p2p First Attempt Timestamp = "
+            << utils::ToString(p2p_first_attempt_timestamp_);
+  CHECK(prefs_);
+  int64_t stored_value = time.ToInternalValue();
+  prefs_->SetInt64(kPrefsP2PFirstAttemptTimestamp, stored_value);
+}
+
+void PayloadState::LoadP2PFirstAttemptTimestamp() {
+  int64_t stored_value = GetPersistedValue(kPrefsP2PFirstAttemptTimestamp);
+  Time stored_time = Time::FromInternalValue(stored_value);
+  SetP2PFirstAttemptTimestamp(stored_time);
+}
+
+void PayloadState::P2PNewAttempt() {
+  CHECK(prefs_);
+  // Set timestamp, if it hasn't been set already
+  if (p2p_first_attempt_timestamp_.is_null()) {
+    SetP2PFirstAttemptTimestamp(system_state_->clock()->GetWallclockTime());
+  }
+  // Increase number of attempts
+  SetP2PNumAttempts(GetP2PNumAttempts() + 1);
+}
+
+bool PayloadState::P2PAttemptAllowed() {
+  if (p2p_num_attempts_ > kMaxP2PAttempts) {
+    LOG(INFO) << "Number of p2p attempts is " << p2p_num_attempts_
+              << " which is greater than "
+              << kMaxP2PAttempts
+              << " - disallowing p2p.";
+    return false;
+  }
+
+  if (!p2p_first_attempt_timestamp_.is_null()) {
+    Time now = system_state_->clock()->GetWallclockTime();
+    TimeDelta time_spent_attempting_p2p = now - p2p_first_attempt_timestamp_;
+    if (time_spent_attempting_p2p.InSeconds() < 0) {
+      LOG(ERROR) << "Time spent attempting p2p is negative"
+                 << " - disallowing p2p.";
+      return false;
+    }
+    if (time_spent_attempting_p2p.InSeconds() > kMaxP2PAttemptTimeSeconds) {
+      LOG(INFO) << "Time spent attempting p2p is "
+                << utils::FormatTimeDelta(time_spent_attempting_p2p)
+                << " which is greater than "
+                << utils::FormatTimeDelta(TimeDelta::FromSeconds(
+                       kMaxP2PAttemptTimeSeconds))
+                << " - disallowing p2p.";
+      return false;
+    }
+  }
+
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/payload_state.h b/payload_state.h
new file mode 100644
index 0000000..bec5823
--- /dev/null
+++ b/payload_state.h
@@ -0,0 +1,573 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_STATE_H_
+#define UPDATE_ENGINE_PAYLOAD_STATE_H_
+
+#include <string>
+#include <vector>
+
+#include <base/time/time.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/metrics.h"
+#include "update_engine/payload_state_interface.h"
+
+namespace chromeos_update_engine {
+
+class SystemState;
+
+// Encapsulates all the payload state required for download. This includes the
+// state necessary for handling multiple URLs in Omaha response, the backoff
+// state, etc. All state is persisted so that we use the most recently saved
+// value when resuming the update_engine process. All state is also cached in
+// memory so that we ensure we always make progress based on last known good
+// state even when there's any issue in reading/writing from the file system.
+class PayloadState : public PayloadStateInterface {
+ public:
+  PayloadState();
+  ~PayloadState() override {}
+
+  // Initializes a payload state object using the given global system state.
+  // It performs the initial loading of all persisted state into memory and
+  // dumps the initial state for debugging purposes.  Note: the other methods
+  // should be called only after calling Initialize on this object.
+  bool Initialize(SystemState* system_state);
+
+  // Implementation of PayloadStateInterface methods.
+  void SetResponse(const OmahaResponse& response) override;
+  void DownloadComplete() override;
+  void DownloadProgress(size_t count) override;
+  void UpdateResumed() override;
+  void UpdateRestarted() override;
+  void UpdateSucceeded() override;
+  void UpdateFailed(ErrorCode error) override;
+  void ResetUpdateStatus() override;
+  bool ShouldBackoffDownload() override;
+  void Rollback() override;
+  void ExpectRebootInNewVersion(const std::string& target_version_uid) override;
+  void SetUsingP2PForDownloading(bool value) override;
+
+  void SetUsingP2PForSharing(bool value) override {
+    using_p2p_for_sharing_ = value;
+  }
+
+  inline std::string GetResponseSignature() override {
+    return response_signature_;
+  }
+
+  inline int GetFullPayloadAttemptNumber() override {
+    return full_payload_attempt_number_;
+  }
+
+  inline int GetPayloadAttemptNumber() override {
+    return payload_attempt_number_;
+  }
+
+  inline std::string GetCurrentUrl() override {
+    return candidate_urls_.size() ? candidate_urls_[url_index_] : "";
+  }
+
+  inline uint32_t GetUrlFailureCount() override {
+    return url_failure_count_;
+  }
+
+  inline uint32_t GetUrlSwitchCount() override {
+    return url_switch_count_;
+  }
+
+  inline int GetNumResponsesSeen() override {
+    return num_responses_seen_;
+  }
+
+  inline base::Time GetBackoffExpiryTime() override {
+    return backoff_expiry_time_;
+  }
+
+  base::TimeDelta GetUpdateDuration() override;
+
+  base::TimeDelta GetUpdateDurationUptime() override;
+
+  inline uint64_t GetCurrentBytesDownloaded(DownloadSource source) override {
+    return source < kNumDownloadSources ? current_bytes_downloaded_[source] : 0;
+  }
+
+  inline uint64_t GetTotalBytesDownloaded(DownloadSource source) override {
+    return source < kNumDownloadSources ? total_bytes_downloaded_[source] : 0;
+  }
+
+  inline uint32_t GetNumReboots() override {
+    return num_reboots_;
+  }
+
+  void UpdateEngineStarted() override;
+
+  inline std::string GetRollbackVersion() override {
+    return rollback_version_;
+  }
+
+  int GetP2PNumAttempts() override;
+  base::Time GetP2PFirstAttemptTimestamp() override;
+  void P2PNewAttempt() override;
+  bool P2PAttemptAllowed() override;
+
+  bool GetUsingP2PForDownloading() const override {
+    return using_p2p_for_downloading_;
+  }
+
+  bool GetUsingP2PForSharing() const override {
+    return using_p2p_for_sharing_;
+  }
+
+  base::TimeDelta GetScatteringWaitPeriod() override {
+    return scattering_wait_period_;
+  }
+
+  void SetScatteringWaitPeriod(base::TimeDelta wait_period) override;
+
+  void SetP2PUrl(const std::string& url) override {
+    p2p_url_ = url;
+  }
+
+  std::string GetP2PUrl() const override {
+    return p2p_url_;
+  }
+
+ private:
+  enum class AttemptType {
+    kUpdate,
+    kRollback,
+  };
+
+  friend class PayloadStateTest;
+  FRIEND_TEST(PayloadStateTest, RebootAfterUpdateFailedMetric);
+  FRIEND_TEST(PayloadStateTest, RebootAfterUpdateSucceed);
+  FRIEND_TEST(PayloadStateTest, RebootAfterCanceledUpdate);
+  FRIEND_TEST(PayloadStateTest, RollbackVersion);
+  FRIEND_TEST(PayloadStateTest, UpdateSuccessWithWipedPrefs);
+
+  // Helper called when an attempt has begun, is called by
+  // UpdateResumed(), UpdateRestarted() and Rollback().
+  void AttemptStarted(AttemptType attempt_type);
+
+  // Increments the payload attempt number used for metrics.
+  void IncrementPayloadAttemptNumber();
+
+  // Increments the payload attempt number which governs the backoff behavior
+  // at the time of the next update check.
+  void IncrementFullPayloadAttemptNumber();
+
+  // Advances the current URL index to the next available one. If all URLs have
+  // been exhausted during the current payload download attempt (as indicated
+  // by the payload attempt number), then it will increment the payload attempt
+  // number and wrap around again with the first URL in the list. This also
+  // updates the URL switch count, if needed.
+  void IncrementUrlIndex();
+
+  // Increments the failure count of the current URL. If the configured max
+  // failure count is reached for this URL, it advances the current URL index
+  // to the next URL and resets the failure count for that URL.
+  void IncrementFailureCount();
+
+  // Updates the backoff expiry time exponentially based on the current
+  // payload attempt number.
+  void UpdateBackoffExpiryTime();
+
+  // Updates the value of current download source based on the current URL
+  // index. If the download source is not one of the known sources, it's set
+  // to kNumDownloadSources.
+  void UpdateCurrentDownloadSource();
+
+  // Updates the various metrics corresponding with the given number of bytes
+  // that were downloaded recently.
+  void UpdateBytesDownloaded(size_t count);
+
+  // Calculates the PayloadType we're using.
+  PayloadType CalculatePayloadType();
+
+  // Collects and reports the various metrics related to an update attempt.
+  void CollectAndReportAttemptMetrics(ErrorCode code);
+
+  // Persists values related to the UpdateEngine.Attempt.* metrics so
+  // we can identify later if an update attempt ends abnormally.
+  void PersistAttemptMetrics();
+
+  // Clears persistent state previously set using AttemptMetricsPersist().
+  void ClearPersistedAttemptMetrics();
+
+  // Checks if persistent state previously set using AttemptMetricsPersist()
+  // exists and, if so, emits it with |attempt_result| set to
+  // metrics::AttemptResult::kAbnormalTermination.
+  void ReportAndClearPersistedAttemptMetrics();
+
+  // Collects and reports the various metrics related to a successful update.
+  void CollectAndReportSuccessfulUpdateMetrics();
+
+  // Checks if we were expecting to be running in the new version but the
+  // boot into the new version failed for some reason. If that's the case, an
+  // UMA metric is sent reporting the number of attempts the same applied
+  // payload was attempted to reboot. This function is called by UpdateAttempter
+  // every time the update engine starts and there's no reboot pending.
+  void ReportFailedBootIfNeeded();
+
+  // Resets all the persisted state values which are maintained relative to the
+  // current response signature. The response signature itself is not reset.
+  void ResetPersistedState();
+
+  // Resets the appropriate state related to download sources that need to be
+  // reset on a new update.
+  void ResetDownloadSourcesOnNewUpdate();
+
+  // Returns the persisted value from prefs_ for the given key. It also
+  // validates that the value returned is non-negative.
+  int64_t GetPersistedValue(const std::string& key);
+
+  // Calculates the response "signature", which is basically a string composed
+  // of the subset of the fields in the current response that affect the
+  // behavior of the PayloadState.
+  std::string CalculateResponseSignature();
+
+  // Initializes the current response signature from the persisted state.
+  void LoadResponseSignature();
+
+  // Sets the response signature to the given value. Also persists the value
+  // being set so that we resume from the save value in case of a process
+  // restart.
+  void SetResponseSignature(const std::string& response_signature);
+
+  // Initializes the payload attempt number from the persisted state.
+  void LoadPayloadAttemptNumber();
+
+  // Initializes the payload attempt number for full payloads from the persisted
+  // state.
+  void LoadFullPayloadAttemptNumber();
+
+  // Sets the payload attempt number to the given value. Also persists the
+  // value being set so that we resume from the same value in case of a process
+  // restart.
+  void SetPayloadAttemptNumber(int payload_attempt_number);
+
+  // Sets the payload attempt number for full updates to the given value. Also
+  // persists the value being set so that we resume from the same value in case
+  // of a process restart.
+  void SetFullPayloadAttemptNumber(int payload_attempt_number);
+
+  // Initializes the current URL index from the persisted state.
+  void LoadUrlIndex();
+
+  // Sets the current URL index to the given value. Also persists the value
+  // being set so that we resume from the same value in case of a process
+  // restart.
+  void SetUrlIndex(uint32_t url_index);
+
+  // Initializes the current URL's failure count from the persisted stae.
+  void LoadUrlFailureCount();
+
+  // Sets the current URL's failure count to the given value. Also persists the
+  // value being set so that we resume from the same value in case of a process
+  // restart.
+  void SetUrlFailureCount(uint32_t url_failure_count);
+
+  // Sets |url_switch_count_| to the given value and persists the value.
+  void SetUrlSwitchCount(uint32_t url_switch_count);
+
+  // Initializes |url_switch_count_| from the persisted stae.
+  void LoadUrlSwitchCount();
+
+  // Initializes the backoff expiry time from the persisted state.
+  void LoadBackoffExpiryTime();
+
+  // Sets the backoff expiry time to the given value. Also persists the value
+  // being set so that we resume from the same value in case of a process
+  // restart.
+  void SetBackoffExpiryTime(const base::Time& new_time);
+
+  // Initializes |update_timestamp_start_| from the persisted state.
+  void LoadUpdateTimestampStart();
+
+  // Sets |update_timestamp_start_| to the given value and persists the value.
+  void SetUpdateTimestampStart(const base::Time& value);
+
+  // Sets |update_timestamp_end_| to the given value. This is not persisted
+  // as it happens at the end of the update process where state is deleted
+  // anyway.
+  void SetUpdateTimestampEnd(const base::Time& value);
+
+  // Initializes |update_duration_uptime_| from the persisted state.
+  void LoadUpdateDurationUptime();
+
+  // Helper method used in SetUpdateDurationUptime() and
+  // CalculateUpdateDurationUptime().
+  void SetUpdateDurationUptimeExtended(const base::TimeDelta& value,
+                                       const base::Time& timestamp,
+                                       bool use_logging);
+
+  // Sets |update_duration_uptime_| to the given value and persists
+  // the value and sets |update_duration_uptime_timestamp_| to the
+  // current monotonic time.
+  void SetUpdateDurationUptime(const base::TimeDelta& value);
+
+  // Adds the difference between current monotonic time and
+  // |update_duration_uptime_timestamp_| to |update_duration_uptime_| and
+  // sets |update_duration_uptime_timestamp_| to current monotonic time.
+  void CalculateUpdateDurationUptime();
+
+  // Returns the full key for a download source given the prefix.
+  std::string GetPrefsKey(const std::string& prefix, DownloadSource source);
+
+  // Loads the number of bytes that have been currently downloaded through the
+  // previous attempts from the persisted state for the given source. It's
+  // reset to 0 everytime we begin a full update and is continued from previous
+  // attempt if we're resuming the update.
+  void LoadCurrentBytesDownloaded(DownloadSource source);
+
+  // Sets the number of bytes that have been currently downloaded for the
+  // given source. This value is also persisted.
+  void SetCurrentBytesDownloaded(DownloadSource source,
+                                 uint64_t current_bytes_downloaded,
+                                 bool log);
+
+  // Loads the total number of bytes that have been downloaded (since the last
+  // successful update) from the persisted state for the given source. It's
+  // reset to 0 everytime we successfully apply an update and counts the bytes
+  // downloaded for both successful and failed attempts since then.
+  void LoadTotalBytesDownloaded(DownloadSource source);
+
+  // Sets the total number of bytes that have been downloaded so far for the
+  // given source. This value is also persisted.
+  void SetTotalBytesDownloaded(DownloadSource source,
+                               uint64_t total_bytes_downloaded,
+                               bool log);
+
+  // Loads the blacklisted version from our prefs file.
+  void LoadRollbackVersion();
+
+  // Blacklists this version from getting AU'd to until we receive a new update
+  // response.
+  void SetRollbackVersion(const std::string& rollback_version);
+
+  // Clears any blacklisted version.
+  void ResetRollbackVersion();
+
+  inline uint32_t GetUrlIndex() {
+    return url_index_;
+  }
+
+  // Computes the list of candidate URLs from the total list of payload URLs in
+  // the Omaha response.
+  void ComputeCandidateUrls();
+
+  // Sets |num_responses_seen_| and persist it to disk.
+  void SetNumResponsesSeen(int num_responses_seen);
+
+  // Initializes |num_responses_seen_| from persisted state.
+  void LoadNumResponsesSeen();
+
+  // Initializes |num_reboots_| from the persisted state.
+  void LoadNumReboots();
+
+  // Sets |num_reboots| for the update attempt. Also persists the
+  // value being set so that we resume from the same value in case of a process
+  // restart.
+  void SetNumReboots(uint32_t num_reboots);
+
+  // Checks to see if the device rebooted since the last call and if so
+  // increments num_reboots.
+  void UpdateNumReboots();
+
+  // Writes the current wall-clock time to the kPrefsSystemUpdatedMarker
+  // state variable.
+  void CreateSystemUpdatedMarkerFile();
+
+  // Called at program startup if the device booted into a new update.
+  // The |time_to_reboot| parameter contains the (wall-clock) duration
+  // from when the update successfully completed (the value written
+  // into the kPrefsSystemUpdatedMarker state variable) until the device
+  // was booted into the update (current wall-clock time).
+  void BootedIntoUpdate(base::TimeDelta time_to_reboot);
+
+  // Loads the |kPrefsP2PFirstAttemptTimestamp| state variable from disk
+  // into |p2p_first_attempt_timestamp_|.
+  void LoadP2PFirstAttemptTimestamp();
+
+  // Loads the |kPrefsP2PNumAttempts| state variable into |p2p_num_attempts_|.
+  void LoadP2PNumAttempts();
+
+  // Sets the |kPrefsP2PNumAttempts| state variable to |value|.
+  void SetP2PNumAttempts(int value);
+
+  // Sets the |kPrefsP2PFirstAttemptTimestamp| state variable to |time|.
+  void SetP2PFirstAttemptTimestamp(const base::Time& time);
+
+  // Loads the persisted scattering wallclock-based wait period.
+  void LoadScatteringWaitPeriod();
+
+  // The global state of the system.
+  SystemState* system_state_;
+
+  // Interface object with which we read/write persisted state. This must
+  // be set by calling the Initialize method before calling any other method.
+  PrefsInterface* prefs_;
+
+  // Interface object with which we read/write persisted state. This must
+  // be set by calling the Initialize method before calling any other method.
+  // This object persists across powerwashes.
+  PrefsInterface* powerwash_safe_prefs_;
+
+  // This is the current response object from Omaha.
+  OmahaResponse response_;
+
+  // Whether P2P is being used for downloading and sharing.
+  bool using_p2p_for_downloading_;
+  bool using_p2p_for_sharing_;
+
+  // Stores the P2P download URL, if one is used.
+  std::string p2p_url_;
+
+  // The cached value of |kPrefsP2PFirstAttemptTimestamp|.
+  base::Time p2p_first_attempt_timestamp_;
+
+  // The cached value of |kPrefsP2PNumAttempts|.
+  int p2p_num_attempts_;
+
+  // This stores a "signature" of the current response. The signature here
+  // refers to a subset of the current response from Omaha.  Each update to
+  // this value is persisted so we resume from the same value in case of a
+  // process restart.
+  std::string response_signature_;
+
+  // The number of times we've tried to download the payload. This is
+  // incremented each time we download the payload successsfully or when we
+  // exhaust all failure limits for all URLs and are about to wrap around back
+  // to the first URL.  Each update to this value is persisted so we resume from
+  // the same value in case of a process restart.
+  int payload_attempt_number_;
+
+  // The number of times we've tried to download the payload in full. This is
+  // incremented each time we download the payload in full successsfully or
+  // when we exhaust all failure limits for all URLs and are about to wrap
+  // around back to the first URL.  Each update to this value is persisted so
+  // we resume from the same value in case of a process restart.
+  int full_payload_attempt_number_;
+
+  // The index of the current URL.  This type is different from the one in the
+  // accessor methods because PrefsInterface supports only int64_t but we want
+  // to provide a stronger abstraction of uint32_t.  Each update to this value
+  // is persisted so we resume from the same value in case of a process
+  // restart.
+  int64_t url_index_;
+
+  // The count of failures encountered in the current attempt to download using
+  // the current URL (specified by url_index_).  Each update to this value is
+  // persisted so we resume from the same value in case of a process restart.
+  int64_t url_failure_count_;
+
+  // The number of times we've switched URLs.
+  int32_t url_switch_count_;
+
+  // The current download source based on the current URL. This value is
+  // not persisted as it can be recomputed everytime we update the URL.
+  // We're storing this so as not to recompute this on every few bytes of
+  // data we read from the socket.
+  DownloadSource current_download_source_;
+
+  // The number of different Omaha responses seen. Increases every time
+  // a new response is seen. Resets to 0 only when the system has been
+  // successfully updated.
+  int num_responses_seen_;
+
+  // The number of system reboots during an update attempt. Technically since
+  // we don't go out of our way to not update it when not attempting an update,
+  // also records the number of reboots before the next update attempt starts.
+  uint32_t num_reboots_;
+
+  // The timestamp until which we've to wait before attempting to download the
+  // payload again, so as to backoff repeated downloads.
+  base::Time backoff_expiry_time_;
+
+  // The most recently calculated value of the update duration.
+  base::TimeDelta update_duration_current_;
+
+  // The point in time (wall-clock) that the update was started.
+  base::Time update_timestamp_start_;
+
+  // The point in time (wall-clock) that the update ended. If the update
+  // is still in progress, this is set to the Epoch (e.g. 0).
+  base::Time update_timestamp_end_;
+
+  // The update duration uptime
+  base::TimeDelta update_duration_uptime_;
+
+  // The monotonic time when |update_duration_uptime_| was last set
+  base::Time update_duration_uptime_timestamp_;
+
+  // The number of bytes that have been downloaded for each source for each new
+  // update attempt. If we resume an update, we'll continue from the previous
+  // value, but if we get a new response or if the previous attempt failed,
+  // we'll reset this to 0 to start afresh. Each update to this value is
+  // persisted so we resume from the same value in case of a process restart.
+  // The extra index in the array is to no-op accidental access in case the
+  // return value from GetCurrentDownloadSource is used without validation.
+  uint64_t current_bytes_downloaded_[kNumDownloadSources + 1];
+
+  // The number of bytes that have been downloaded for each source since the
+  // the last successful update. This is used to compute the overhead we incur.
+  // Each update to this value is persisted so we resume from the same value in
+  // case of a process restart.
+  // The extra index in the array is to no-op accidental access in case the
+  // return value from GetCurrentDownloadSource is used without validation.
+  uint64_t total_bytes_downloaded_[kNumDownloadSources + 1];
+
+  // A small timespan used when comparing wall-clock times for coping
+  // with the fact that clocks drift and consequently are adjusted
+  // (either forwards or backwards) via NTP.
+  static const base::TimeDelta kDurationSlack;
+
+  // The ordered list of the subset of payload URL candidates which are
+  // allowed as per device policy.
+  std::vector<std::string> candidate_urls_;
+
+  // This stores a blacklisted version set as part of rollback. When we rollback
+  // we store the version of the os from which we are rolling back from in order
+  // to guarantee that we do not re-update to it on the next au attempt after
+  // reboot.
+  std::string rollback_version_;
+
+  // The number of bytes downloaded per attempt.
+  int64_t attempt_num_bytes_downloaded_;
+
+  // The boot time when the attempt was started.
+  base::Time attempt_start_time_boot_;
+
+  // The monotonic time when the attempt was started.
+  base::Time attempt_start_time_monotonic_;
+
+  // The connection type when the attempt started.
+  metrics::ConnectionType attempt_connection_type_;
+
+  // Whether we're currently rolling back.
+  AttemptType attempt_type_;
+
+  // The current scattering wallclock-based wait period.
+  base::TimeDelta scattering_wait_period_;
+
+  DISALLOW_COPY_AND_ASSIGN(PayloadState);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_STATE_H_
diff --git a/payload_state_interface.h b/payload_state_interface.h
new file mode 100644
index 0000000..40a13dd
--- /dev/null
+++ b/payload_state_interface.h
@@ -0,0 +1,199 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_PAYLOAD_STATE_INTERFACE_H_
+#define UPDATE_ENGINE_PAYLOAD_STATE_INTERFACE_H_
+
+#include <string>
+
+#include "update_engine/common/action_processor.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/omaha_response.h"
+
+namespace chromeos_update_engine {
+
+// Describes the methods that need to be implemented by the PayloadState class.
+// This interface has been carved out to support mocking of the PayloadState
+// object.
+class PayloadStateInterface {
+ public:
+  virtual ~PayloadStateInterface() = default;
+
+  // Sets the internal payload state based on the given Omaha response. This
+  // response could be the same or different from the one for which we've stored
+  // the internal state. If it's different, then this method resets all the
+  // internal state corresponding to the old response. Since the Omaha response
+  // has a lot of fields that are not related to payload state, it uses only
+  // a subset of the fields in the Omaha response to compare equality.
+  virtual void SetResponse(const OmahaResponse& response) = 0;
+
+  // This method should be called whenever we have completed downloading all
+  // the bytes of a payload and have verified that its size and hash match the
+  // expected values. We use this notificaiton to increment the payload attempt
+  // number so that the throttle the next attempt to download the same payload
+  // (in case there's an error in subsequent steps such as post-install)
+  // appropriately.
+  virtual void DownloadComplete() = 0;
+
+  // This method should be called whenever we receive new bytes from the
+  // network for the current payload. We use this notification to reset the
+  // failure count for a given URL since receipt of some bytes means we are
+  // able to make forward progress with the current URL.
+  virtual void DownloadProgress(size_t count) = 0;
+
+  // This method should be called every time we resume an update attempt.
+  virtual void UpdateResumed() = 0;
+
+  // This method should be called every time we begin a new update. This method
+  // should not be called when we resume an update from the previously
+  // downloaded point. This is used to reset the metrics for each new update.
+  virtual void UpdateRestarted() = 0;
+
+  // This method should be called once after an update attempt succeeds. This
+  // is when the relevant UMA metrics that are tracked on a per-update-basis
+  // are uploaded to the UMA server.
+  virtual void UpdateSucceeded() = 0;
+
+  // This method should be called whenever an update attempt fails with the
+  // given error code. We use this notification to update the payload state
+  // depending on the type of the error that happened.
+  virtual void UpdateFailed(ErrorCode error) = 0;
+
+  // This method should be called whenever a succeeded update is canceled, and
+  // thus can only be called after UpdateSucceeded(). This is currently used
+  // only for manual testing using the update_engine_client.
+  virtual void ResetUpdateStatus() = 0;
+
+  // This method should be called every time we initiate a Rollback.
+  virtual void Rollback() = 0;
+
+  // Sets the expectations to boot into the new version in the next reboot.
+  // This function is called every time a new update is marked as ready by
+  // UpdateSuccess(). |target_version_uid| is an unique identifier of the
+  // applied payload. It can be any string, as long as the same string is used
+  // for the same payload.
+  virtual void ExpectRebootInNewVersion(
+      const std::string& target_version_uid) = 0;
+
+  // Sets whether P2P is being used to download the update payload. This
+  // is used to keep track of download sources being used and should be called
+  // before the transfer begins.
+  virtual void SetUsingP2PForDownloading(bool value) = 0;
+
+  // Sets whether P2P is being used for sharing the update payloads.
+  virtual void SetUsingP2PForSharing(bool value) = 0;
+
+  // Returns true if we should backoff the current download attempt.
+  // False otherwise.
+  virtual bool ShouldBackoffDownload() = 0;
+
+  // Returns the currently stored response "signature". The signature  is a
+  // subset of fields that are of interest to the PayloadState behavior.
+  virtual std::string GetResponseSignature() = 0;
+
+  // Returns the payload attempt number.
+  virtual int GetPayloadAttemptNumber() = 0;
+
+  // Returns the payload attempt number of the attempted full payload. Returns
+  // 0 for delta payloads.
+  virtual int GetFullPayloadAttemptNumber() = 0;
+
+  // Returns the current URL. Returns an empty string if there's no valid URL.
+  virtual std::string GetCurrentUrl() = 0;
+
+  // Returns the current URL's failure count.
+  virtual uint32_t GetUrlFailureCount() = 0;
+
+  // Returns the total number of times a new URL has been switched to
+  // for the current response.
+  virtual uint32_t GetUrlSwitchCount() = 0;
+
+  // Returns the total number of different responses seen since the
+  // last successful update.
+  virtual int GetNumResponsesSeen() = 0;
+
+  // Returns the expiry time for the current backoff period.
+  virtual base::Time GetBackoffExpiryTime() = 0;
+
+  // Returns the elapsed time used for this update, including time
+  // where the device is powered off and sleeping. If the
+  // update has not completed, returns the time spent so far.
+  virtual base::TimeDelta GetUpdateDuration() = 0;
+
+  // Returns the time used for this update not including time when
+  // the device is powered off or sleeping. If the update has not
+  // completed, returns the time spent so far.
+  virtual base::TimeDelta GetUpdateDurationUptime() = 0;
+
+  // Returns the number of bytes that have been downloaded for each source for
+  // each new update attempt. If we resume an update, we'll continue from the
+  // previous value, but if we get a new response or if the previous attempt
+  // failed, we'll reset this to 0 to start afresh.
+  virtual uint64_t GetCurrentBytesDownloaded(DownloadSource source) = 0;
+
+  // Returns the total number of bytes that have been downloaded for each
+  // source since the the last successful update. This is used to compute the
+  // overhead we incur.
+  virtual uint64_t GetTotalBytesDownloaded(DownloadSource source) = 0;
+
+  // Returns the reboot count for this update attempt.
+  virtual uint32_t GetNumReboots() = 0;
+
+  // Called at update_engine startup to do various house-keeping.
+  virtual void UpdateEngineStarted() = 0;
+
+  // Returns the version from before a rollback if our last update was a
+  // rollback.
+  virtual std::string GetRollbackVersion() = 0;
+
+  // Returns the value of number of attempts we've attempted to
+  // download the payload via p2p.
+  virtual int GetP2PNumAttempts() = 0;
+
+  // Returns the value of timestamp of the first time we've attempted
+  // to download the payload via p2p.
+  virtual base::Time GetP2PFirstAttemptTimestamp() = 0;
+
+  // Should be called every time we decide to use p2p for an update
+  // attempt. This is used to increase the p2p attempt counter and
+  // set the timestamp for first attempt.
+  virtual void P2PNewAttempt() = 0;
+
+  // Returns |true| if we are allowed to continue using p2p for
+  // downloading and |false| otherwise. This is done by recording
+  // and examining how many attempts have been done already as well
+  // as when the first attempt was.
+  virtual bool P2PAttemptAllowed() = 0;
+
+  // Gets the values previously set with SetUsingP2PForDownloading() and
+  // SetUsingP2PForSharing().
+  virtual bool GetUsingP2PForDownloading() const = 0;
+  virtual bool GetUsingP2PForSharing() const = 0;
+
+  // Returns the current (persisted) scattering wallclock-based wait period.
+  virtual base::TimeDelta GetScatteringWaitPeriod() = 0;
+
+  // Sets and persists the scattering wallclock-based wait period.
+  virtual void SetScatteringWaitPeriod(base::TimeDelta wait_period) = 0;
+
+  // Sets/gets the P2P download URL, if one is to be used.
+  virtual void SetP2PUrl(const std::string& url) = 0;
+  virtual std::string GetP2PUrl() const = 0;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PAYLOAD_STATE_INTERFACE_H_
diff --git a/payload_state_unittest.cc b/payload_state_unittest.cc
new file mode 100644
index 0000000..a8067dc
--- /dev/null
+++ b/payload_state_unittest.cc
@@ -0,0 +1,1663 @@
+//
+// Copyright (C) 2012 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 "update_engine/payload_state.h"
+
+#include <base/files/file_path.h>
+#include <base/files/file_util.h>
+#include <base/strings/stringprintf.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/common/mock_prefs.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/omaha_request_action.h"
+
+using base::Time;
+using base::TimeDelta;
+using std::string;
+using testing::AnyNumber;
+using testing::AtLeast;
+using testing::Mock;
+using testing::NiceMock;
+using testing::Return;
+using testing::SetArgumentPointee;
+using testing::_;
+
+namespace chromeos_update_engine {
+
+const char* kCurrentBytesDownloadedFromHttps =
+  "current-bytes-downloaded-from-HttpsServer";
+const char* kTotalBytesDownloadedFromHttps =
+  "total-bytes-downloaded-from-HttpsServer";
+const char* kCurrentBytesDownloadedFromHttp =
+  "current-bytes-downloaded-from-HttpServer";
+const char* kTotalBytesDownloadedFromHttp =
+  "total-bytes-downloaded-from-HttpServer";
+const char* kCurrentBytesDownloadedFromHttpPeer =
+  "current-bytes-downloaded-from-HttpPeer";
+const char* kTotalBytesDownloadedFromHttpPeer =
+  "total-bytes-downloaded-from-HttpPeer";
+
+static void SetupPayloadStateWith2Urls(string hash,
+                                       bool http_enabled,
+                                       PayloadState* payload_state,
+                                       OmahaResponse* response) {
+  response->payload_urls.clear();
+  response->payload_urls.push_back("http://test");
+  response->payload_urls.push_back("https://test");
+  response->size = 523456789;
+  response->hash = hash;
+  response->metadata_size = 558123;
+  response->metadata_signature = "metasign";
+  response->max_failure_count_per_url = 3;
+  payload_state->SetResponse(*response);
+  string stored_response_sign = payload_state->GetResponseSignature();
+
+  string expected_url_https_only =
+      "NumURLs = 1\n"
+      "Candidate Url0 = https://test\n";
+
+  string expected_urls_both =
+      "NumURLs = 2\n"
+      "Candidate Url0 = http://test\n"
+      "Candidate Url1 = https://test\n";
+
+  string expected_response_sign =
+      (http_enabled ? expected_urls_both : expected_url_https_only) +
+      base::StringPrintf("Payload Size = 523456789\n"
+                         "Payload Sha256 Hash = %s\n"
+                         "Metadata Size = 558123\n"
+                         "Metadata Signature = metasign\n"
+                         "Is Delta Payload = %d\n"
+                         "Max Failure Count Per Url = %d\n"
+                         "Disable Payload Backoff = %d\n",
+                         hash.c_str(),
+                         response->is_delta_payload,
+                         response->max_failure_count_per_url,
+                         response->disable_payload_backoff);
+  EXPECT_EQ(expected_response_sign, stored_response_sign);
+}
+
+class PayloadStateTest : public ::testing::Test { };
+
+TEST(PayloadStateTest, DidYouAddANewErrorCode) {
+  if (static_cast<int>(ErrorCode::kUmaReportedMax) != 48) {
+    LOG(ERROR) << "The following failure is intentional. If you added a new "
+               << "ErrorCode enum value, make sure to add it to the "
+               << "PayloadState::UpdateFailed method and then update this test "
+               << "to the new value of ErrorCode::kUmaReportedMax, which is "
+               << ErrorCode::kUmaReportedMax;
+    EXPECT_FALSE("Please see the log line above");
+  }
+}
+
+TEST(PayloadStateTest, SetResponseWorksWithEmptyResponse) {
+  OmahaResponse response;
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0)).Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttpPeer, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0)).Times(AtLeast(1));
+  PayloadState payload_state;
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  payload_state.SetResponse(response);
+  string stored_response_sign = payload_state.GetResponseSignature();
+  string expected_response_sign = "NumURLs = 0\n"
+                                  "Payload Size = 0\n"
+                                  "Payload Sha256 Hash = \n"
+                                  "Metadata Size = 0\n"
+                                  "Metadata Signature = \n"
+                                  "Is Delta Payload = 0\n"
+                                  "Max Failure Count Per Url = 0\n"
+                                  "Disable Payload Backoff = 0\n";
+  EXPECT_EQ(expected_response_sign, stored_response_sign);
+  EXPECT_EQ("", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+}
+
+TEST(PayloadStateTest, SetResponseWorksWithSingleUrl) {
+  OmahaResponse response;
+  response.payload_urls.push_back("https://single.url.test");
+  response.size = 123456789;
+  response.hash = "hash";
+  response.metadata_size = 58123;
+  response.metadata_signature = "msign";
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttpPeer, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
+      .Times(AtLeast(1));
+  PayloadState payload_state;
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  payload_state.SetResponse(response);
+  string stored_response_sign = payload_state.GetResponseSignature();
+  string expected_response_sign = "NumURLs = 1\n"
+                                  "Candidate Url0 = https://single.url.test\n"
+                                  "Payload Size = 123456789\n"
+                                  "Payload Sha256 Hash = hash\n"
+                                  "Metadata Size = 58123\n"
+                                  "Metadata Signature = msign\n"
+                                  "Is Delta Payload = 0\n"
+                                  "Max Failure Count Per Url = 0\n"
+                                  "Disable Payload Backoff = 0\n";
+  EXPECT_EQ(expected_response_sign, stored_response_sign);
+  EXPECT_EQ("https://single.url.test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+}
+
+TEST(PayloadStateTest, SetResponseWorksWithMultipleUrls) {
+  OmahaResponse response;
+  response.payload_urls.push_back("http://multiple.url.test");
+  response.payload_urls.push_back("https://multiple.url.test");
+  response.size = 523456789;
+  response.hash = "rhash";
+  response.metadata_size = 558123;
+  response.metadata_signature = "metasign";
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttpPeer, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
+      .Times(AtLeast(1));
+
+  PayloadState payload_state;
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  payload_state.SetResponse(response);
+  string stored_response_sign = payload_state.GetResponseSignature();
+  string expected_response_sign = "NumURLs = 2\n"
+                                  "Candidate Url0 = http://multiple.url.test\n"
+                                  "Candidate Url1 = https://multiple.url.test\n"
+                                  "Payload Size = 523456789\n"
+                                  "Payload Sha256 Hash = rhash\n"
+                                  "Metadata Size = 558123\n"
+                                  "Metadata Signature = metasign\n"
+                                  "Is Delta Payload = 0\n"
+                                  "Max Failure Count Per Url = 0\n"
+                                  "Disable Payload Backoff = 0\n";
+  EXPECT_EQ(expected_response_sign, stored_response_sign);
+  EXPECT_EQ("http://multiple.url.test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+}
+
+TEST(PayloadStateTest, CanAdvanceUrlIndexCorrectly) {
+  OmahaResponse response;
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+  PayloadState payload_state;
+
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  // Payload attempt should start with 0 and then advance to 1.
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(AtLeast(2));
+
+  // Reboots will be set
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, _)).Times(AtLeast(1));
+
+  // Url index should go from 0 to 1 twice.
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(AtLeast(1));
+
+  // Failure count should be called each times url index is set, so that's
+  // 4 times for this test.
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(4));
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // This does a SetResponse which causes all the states to be set to 0 for
+  // the first time.
+  SetupPayloadStateWith2Urls("Hash1235", true, &payload_state, &response);
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+
+  // Verify that on the first error, the URL index advances to 1.
+  ErrorCode error = ErrorCode::kDownloadMetadataSignatureMismatch;
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+
+  // Verify that on the next error, the URL index wraps around to 0.
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+
+  // Verify that on the next error, it again advances to 1.
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+
+  // Verify that we switched URLs three times
+  EXPECT_EQ(3, payload_state.GetUrlSwitchCount());
+}
+
+TEST(PayloadStateTest, NewResponseResetsPayloadState) {
+  OmahaResponse response;
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+
+  // Set the first response.
+  SetupPayloadStateWith2Urls("Hash5823", true, &payload_state, &response);
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+
+  // Advance the URL index to 1 by faking an error.
+  ErrorCode error = ErrorCode::kDownloadMetadataSignatureMismatch;
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // Now, slightly change the response and set it again.
+  SetupPayloadStateWith2Urls("Hash8225", true, &payload_state, &response);
+  EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
+
+  // Fake an error again.
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // Return a third different response.
+  SetupPayloadStateWith2Urls("Hash9999", true, &payload_state, &response);
+  EXPECT_EQ(3, payload_state.GetNumResponsesSeen());
+
+  // Make sure the url index was reset to 0 because of the new response.
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+  EXPECT_EQ(0,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
+                 kDownloadSourceHttpsServer));
+  EXPECT_EQ(0,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+}
+
+TEST(PayloadStateTest, AllCountersGetUpdatedProperlyOnErrorCodesAndEvents) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  int progress_bytes = 100;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(2));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 2))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(2));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 2))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _)).Times(AtLeast(4));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0)).Times(AtLeast(4));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 1)).Times(AtLeast(2));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(7));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 1))
+    .Times(AtLeast(2));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 2))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateTimestampStart, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsUpdateDurationUptime, _))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttps, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttpPeer, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kCurrentBytesDownloadedFromHttp, progress_bytes))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kTotalBytesDownloadedFromHttp, progress_bytes))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 0))
+      .Times(AtLeast(1));
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  SetupPayloadStateWith2Urls("Hash5873", true, &payload_state, &response);
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+
+  // This should advance the URL index.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // This should advance the failure count only.
+  payload_state.UpdateFailed(ErrorCode::kDownloadTransferError);
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // This should advance the failure count only.
+  payload_state.UpdateFailed(ErrorCode::kDownloadTransferError);
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(2, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // This should advance the URL index as we've reached the
+  // max failure count and reset the failure count for the new URL index.
+  // This should also wrap around the URL index and thus cause the payload
+  // attempt number to be incremented.
+  payload_state.UpdateFailed(ErrorCode::kDownloadTransferError);
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(2, payload_state.GetUrlSwitchCount());
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+
+  // This should advance the URL index.
+  payload_state.UpdateFailed(ErrorCode::kPayloadHashMismatchError);
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(3, payload_state.GetUrlSwitchCount());
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+
+  // This should advance the URL index and payload attempt number due to
+  // wrap-around of URL index.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMissingError);
+  EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+
+  // This HTTP error code should only increase the failure count.
+  payload_state.UpdateFailed(static_cast<ErrorCode>(
+      static_cast<int>(ErrorCode::kOmahaRequestHTTPResponseBase) + 404));
+  EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+
+  // And that failure count should be reset when we download some bytes
+  // afterwards.
+  payload_state.DownloadProgress(progress_bytes);
+  EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(4, payload_state.GetUrlSwitchCount());
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+
+  // Now, slightly change the response and set it again.
+  SetupPayloadStateWith2Urls("Hash8532", true, &payload_state, &response);
+  EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
+
+  // Make sure the url index was reset to 0 because of the new response.
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+}
+
+TEST(PayloadStateTest, PayloadAttemptNumberIncreasesOnSuccessfulFullDownload) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _))
+    .Times(AtLeast(2));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(1));
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // This should just advance the payload attempt number;
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  payload_state.DownloadComplete();
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+}
+
+TEST(PayloadStateTest, PayloadAttemptNumberIncreasesOnSuccessfulDeltaDownload) {
+  OmahaResponse response;
+  response.is_delta_payload = true;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AnyNumber());
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsPayloadAttemptNumber, 1))
+    .Times(AtLeast(1));
+
+  // kPrefsFullPayloadAttemptNumber is not incremented for delta payloads.
+  EXPECT_CALL(*prefs, SetInt64(kPrefsFullPayloadAttemptNumber, 0))
+    .Times(AtLeast(1));
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsBackoffExpiryTime, _))
+    .Times(1);
+
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlIndex, 0))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsCurrentUrlFailureCount, 0))
+    .Times(AtLeast(1));
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // This should just advance the payload attempt number;
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  payload_state.DownloadComplete();
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+}
+
+TEST(PayloadStateTest, SetResponseResetsInvalidUrlIndex) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash4427", true, &payload_state, &response);
+
+  // Generate enough events to advance URL index, failure count and
+  // payload attempt number all to 1.
+  payload_state.DownloadComplete();
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  payload_state.UpdateFailed(ErrorCode::kDownloadTransferError);
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+
+  // Now, simulate a corrupted url index on persisted store which gets
+  // loaded when update_engine restarts. Using a different prefs object
+  // so as to not bother accounting for the uninteresting calls above.
+  FakeSystemState fake_system_state2;
+  NiceMock<MockPrefs>* prefs2 = fake_system_state2.mock_prefs();
+  EXPECT_CALL(*prefs2, Exists(_)).WillRepeatedly(Return(true));
+  EXPECT_CALL(*prefs2, GetInt64(_, _)).Times(AtLeast(1));
+  EXPECT_CALL(*prefs2, GetInt64(kPrefsPayloadAttemptNumber, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs2, GetInt64(kPrefsFullPayloadAttemptNumber, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs2, GetInt64(kPrefsCurrentUrlIndex, _))
+      .WillRepeatedly(DoAll(SetArgumentPointee<1>(2), Return(true)));
+  EXPECT_CALL(*prefs2, GetInt64(kPrefsCurrentUrlFailureCount, _))
+    .Times(AtLeast(1));
+  EXPECT_CALL(*prefs2, GetInt64(kPrefsUrlSwitchCount, _))
+    .Times(AtLeast(1));
+
+  // Note: This will be a different payload object, but the response should
+  // have the same hash as before so as to not trivially reset because the
+  // response was different. We want to specifically test that even if the
+  // response is same, we should reset the state if we find it corrupted.
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state2));
+  SetupPayloadStateWith2Urls("Hash4427", true, &payload_state, &response);
+
+  // Make sure all counters get reset to 0 because of the corrupted URL index
+  // we supplied above.
+  EXPECT_EQ(0, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+}
+
+TEST(PayloadStateTest, NoBackoffInteractiveChecks) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  OmahaRequestParams params(&fake_system_state);
+  params.Init("", "", true);  // is_interactive = True.
+  fake_system_state.set_request_params(&params);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Simulate two failures (enough to cause payload backoff) and check
+  // again that we're ready to re-download without any backoff as this is
+  // an interactive check.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+}
+
+TEST(PayloadStateTest, NoBackoffForP2PUpdates) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  OmahaRequestParams params(&fake_system_state);
+  params.Init("", "", false);  // is_interactive = False.
+  fake_system_state.set_request_params(&params);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Simulate two failures (enough to cause payload backoff) and check
+  // again that we're ready to re-download without any backoff as this is
+  // an interactive check.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  // Set p2p url.
+  payload_state.SetUsingP2PForDownloading(true);
+  payload_state.SetP2PUrl("http://mypeer:52909/path/to/file");
+  // Should not backoff for p2p updates.
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+
+  payload_state.SetP2PUrl("");
+  // No actual p2p update if no url is provided.
+  EXPECT_TRUE(payload_state.ShouldBackoffDownload());
+}
+
+TEST(PayloadStateTest, NoBackoffForDeltaPayloads) {
+  OmahaResponse response;
+  response.is_delta_payload = true;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Simulate a successful download and see that we're ready to download
+  // again without any backoff as this is a delta payload.
+  payload_state.DownloadComplete();
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+
+  // Simulate two failures (enough to cause payload backoff) and check
+  // again that we're ready to re-download without any backoff as this is
+  // a delta payload.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(0, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+}
+
+static void CheckPayloadBackoffState(PayloadState* payload_state,
+                                     int expected_attempt_number,
+                                     TimeDelta expected_days) {
+  payload_state->DownloadComplete();
+  EXPECT_EQ(expected_attempt_number,
+      payload_state->GetFullPayloadAttemptNumber());
+  EXPECT_TRUE(payload_state->ShouldBackoffDownload());
+  Time backoff_expiry_time = payload_state->GetBackoffExpiryTime();
+  // Add 1 hour extra to the 6 hour fuzz check to tolerate edge cases.
+  TimeDelta max_fuzz_delta = TimeDelta::FromHours(7);
+  Time expected_min_time = Time::Now() + expected_days - max_fuzz_delta;
+  Time expected_max_time = Time::Now() + expected_days + max_fuzz_delta;
+  EXPECT_LT(expected_min_time.ToInternalValue(),
+            backoff_expiry_time.ToInternalValue());
+  EXPECT_GT(expected_max_time.ToInternalValue(),
+            backoff_expiry_time.ToInternalValue());
+}
+
+TEST(PayloadStateTest, BackoffPeriodsAreInCorrectRange) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8939", true, &payload_state, &response);
+
+  CheckPayloadBackoffState(&payload_state, 1,  TimeDelta::FromDays(1));
+  CheckPayloadBackoffState(&payload_state, 2,  TimeDelta::FromDays(2));
+  CheckPayloadBackoffState(&payload_state, 3,  TimeDelta::FromDays(4));
+  CheckPayloadBackoffState(&payload_state, 4,  TimeDelta::FromDays(8));
+  CheckPayloadBackoffState(&payload_state, 5,  TimeDelta::FromDays(16));
+  CheckPayloadBackoffState(&payload_state, 6,  TimeDelta::FromDays(16));
+  CheckPayloadBackoffState(&payload_state, 7,  TimeDelta::FromDays(16));
+  CheckPayloadBackoffState(&payload_state, 8,  TimeDelta::FromDays(16));
+  CheckPayloadBackoffState(&payload_state, 9,  TimeDelta::FromDays(16));
+  CheckPayloadBackoffState(&payload_state, 10,  TimeDelta::FromDays(16));
+}
+
+TEST(PayloadStateTest, BackoffLogicCanBeDisabled) {
+  OmahaResponse response;
+  response.disable_payload_backoff = true;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8939", true, &payload_state, &response);
+
+  // Simulate a successful download and see that we are ready to download
+  // again without any backoff.
+  payload_state.DownloadComplete();
+  EXPECT_EQ(1, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(1, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+
+  // Test again, this time by simulating two errors that would cause
+  // the payload attempt number to increment due to wrap around. And
+  // check that we are still ready to re-download without any backoff.
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  payload_state.UpdateFailed(ErrorCode::kDownloadMetadataSignatureMismatch);
+  EXPECT_EQ(2, payload_state.GetPayloadAttemptNumber());
+  EXPECT_EQ(2, payload_state.GetFullPayloadAttemptNumber());
+  EXPECT_FALSE(payload_state.ShouldBackoffDownload());
+}
+
+TEST(PayloadStateTest, BytesDownloadedMetricsGetAddedToCorrectSources) {
+  OmahaResponse response;
+  response.disable_payload_backoff = true;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  int https_total = 0;
+  int http_total = 0;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash3286", true, &payload_state, &response);
+  EXPECT_EQ(1, payload_state.GetNumResponsesSeen());
+
+  // Simulate a previous attempt with in order to set an initial non-zero value
+  // for the total bytes downloaded for HTTP.
+  int prev_chunk = 323456789;
+  http_total += prev_chunk;
+  payload_state.DownloadProgress(prev_chunk);
+
+  // Ensure that the initial values for HTTP reflect this attempt.
+  EXPECT_EQ(prev_chunk,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(http_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+
+  // Change the response hash so as to simulate a new response which will
+  // reset the current bytes downloaded, but not the total bytes downloaded.
+  SetupPayloadStateWith2Urls("Hash9904", true, &payload_state, &response);
+  EXPECT_EQ(2, payload_state.GetNumResponsesSeen());
+
+  // First, simulate successful download of a few bytes over HTTP.
+  int first_chunk = 5000000;
+  http_total += first_chunk;
+  payload_state.DownloadProgress(first_chunk);
+  // Test that first all progress is made on HTTP and none on HTTPS.
+  EXPECT_EQ(first_chunk,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(http_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
+                 kDownloadSourceHttpsServer));
+  EXPECT_EQ(https_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+
+  // Simulate an error that'll cause the url index to point to https.
+  ErrorCode error = ErrorCode::kDownloadMetadataSignatureMismatch;
+  payload_state.UpdateFailed(error);
+
+  // Test that no new progress is made on HTTP and new progress is on HTTPS.
+  int second_chunk = 23456789;
+  https_total += second_chunk;
+  payload_state.DownloadProgress(second_chunk);
+  EXPECT_EQ(first_chunk,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(http_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(second_chunk, payload_state.GetCurrentBytesDownloaded(
+              kDownloadSourceHttpsServer));
+  EXPECT_EQ(https_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+
+  // Simulate error to go back to http.
+  payload_state.UpdateFailed(error);
+  int third_chunk = 32345678;
+  int http_chunk = first_chunk + third_chunk;
+  http_total += third_chunk;
+  payload_state.DownloadProgress(third_chunk);
+
+  // Test that third chunk is again back on HTTP. HTTPS remains on second chunk.
+  EXPECT_EQ(http_chunk,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(http_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(second_chunk, payload_state.GetCurrentBytesDownloaded(
+                 kDownloadSourceHttpsServer));
+  EXPECT_EQ(https_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+
+  // Simulate error (will cause URL switch), set p2p is to be used and
+  // then do 42MB worth of progress
+  payload_state.UpdateFailed(error);
+  payload_state.SetUsingP2PForDownloading(true);
+  int p2p_total = 42 * 1000 * 1000;
+  payload_state.DownloadProgress(p2p_total);
+
+  EXPECT_EQ(p2p_total,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpPeer));
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricSuccessfulUpdateUrlSwitchCount,
+      3, _, _, _));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricSuccessfulUpdateTotalDurationMinutes,
+      _, _, _, _));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricSuccessfulUpdateDownloadOverheadPercentage,
+      314, _, _, _));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricAttemptPayloadType, kPayloadTypeFull, kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricSuccessfulUpdatePayloadType, kPayloadTypeFull,
+      kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricSuccessfulUpdateAttemptCount, 1, _, _, _));
+
+  payload_state.UpdateSucceeded();
+
+  // Make sure the metrics are reset after a successful update.
+  EXPECT_EQ(0,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
+                 kDownloadSourceHttpsServer));
+  EXPECT_EQ(0,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+  EXPECT_EQ(0, payload_state.GetNumResponsesSeen());
+}
+
+TEST(PayloadStateTest, DownloadSourcesUsedIsCorrect) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash3286", true, &payload_state, &response);
+
+  // Simulate progress in order to mark HTTP as one of the sources used.
+  int num_bytes = 42 * 1000 * 1000;
+  payload_state.DownloadProgress(num_bytes);
+
+  // Check that this was done via HTTP.
+  EXPECT_EQ(num_bytes,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(num_bytes,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+
+  // Check that only HTTP is reported as a download source.
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricSuccessfulUpdateDownloadSourcesUsed,
+      (1 << kDownloadSourceHttpServer),
+      _, _, _));
+
+  payload_state.UpdateSucceeded();
+}
+
+TEST(PayloadStateTest, RestartingUpdateResetsMetrics) {
+  OmahaResponse response;
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Set the first response.
+  SetupPayloadStateWith2Urls("Hash5823", true, &payload_state, &response);
+
+  int num_bytes = 10000;
+  payload_state.DownloadProgress(num_bytes);
+  EXPECT_EQ(num_bytes,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(num_bytes,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(0, payload_state.GetCurrentBytesDownloaded(
+                 kDownloadSourceHttpsServer));
+  EXPECT_EQ(0,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpsServer));
+
+  payload_state.UpdateRestarted();
+  // Make sure the current bytes downloaded is reset, but not the total bytes.
+  EXPECT_EQ(0,
+            payload_state.GetCurrentBytesDownloaded(kDownloadSourceHttpServer));
+  EXPECT_EQ(num_bytes,
+            payload_state.GetTotalBytesDownloaded(kDownloadSourceHttpServer));
+}
+
+TEST(PayloadStateTest, NumRebootsIncrementsCorrectly) {
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(AtLeast(0));
+  EXPECT_CALL(*prefs, SetInt64(kPrefsNumReboots, 1)).Times(AtLeast(1));
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  payload_state.UpdateRestarted();
+  EXPECT_EQ(0, payload_state.GetNumReboots());
+
+  fake_system_state.set_system_rebooted(true);
+  payload_state.UpdateResumed();
+  // Num reboots should be incremented because system rebooted detected.
+  EXPECT_EQ(1, payload_state.GetNumReboots());
+
+  fake_system_state.set_system_rebooted(false);
+  payload_state.UpdateResumed();
+  // Num reboots should now be 1 as reboot was not detected.
+  EXPECT_EQ(1, payload_state.GetNumReboots());
+
+  // Restart the update again to verify we set the num of reboots back to 0.
+  payload_state.UpdateRestarted();
+  EXPECT_EQ(0, payload_state.GetNumReboots());
+}
+
+TEST(PayloadStateTest, RollbackVersion) {
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+
+  NiceMock<MockPrefs>* mock_powerwash_safe_prefs =
+      fake_system_state.mock_powerwash_safe_prefs();
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Verify pre-conditions are good.
+  EXPECT_TRUE(payload_state.GetRollbackVersion().empty());
+
+  // Mock out the os version and make sure it's blacklisted correctly.
+  string rollback_version = "2345.0.0";
+  OmahaRequestParams params(&fake_system_state);
+  params.Init(rollback_version, "", false);
+  fake_system_state.set_request_params(&params);
+
+  EXPECT_CALL(*mock_powerwash_safe_prefs, SetString(kPrefsRollbackVersion,
+                                                    rollback_version));
+  payload_state.Rollback();
+
+  EXPECT_EQ(rollback_version, payload_state.GetRollbackVersion());
+
+  // Change it up a little and verify we load it correctly.
+  rollback_version = "2345.0.1";
+  // Let's verify we can reload it correctly.
+  EXPECT_CALL(*mock_powerwash_safe_prefs, GetString(
+      kPrefsRollbackVersion, _)).WillOnce(DoAll(
+          SetArgumentPointee<1>(rollback_version), Return(true)));
+  EXPECT_CALL(*mock_powerwash_safe_prefs, SetString(kPrefsRollbackVersion,
+                                                    rollback_version));
+  payload_state.LoadRollbackVersion();
+  EXPECT_EQ(rollback_version, payload_state.GetRollbackVersion());
+
+  // Check that we report only UpdateEngine.Rollback.* metrics in
+  // UpdateSucceeded().
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
+    .Times(0);
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(0);
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(),
+              SendEnumToUMA(
+                  metrics::kMetricRollbackResult,
+                  static_cast<int>(metrics::RollbackResult::kSuccess),
+                  static_cast<int>(metrics::RollbackResult::kNumConstants)));
+  payload_state.UpdateSucceeded();
+}
+
+TEST(PayloadStateTest, DurationsAreCorrect) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+
+  // Set the clock to a well-known time - 1 second on the wall-clock
+  // and 2 seconds on the monotonic clock
+  fake_clock.SetWallclockTime(Time::FromInternalValue(1000000));
+  fake_clock.SetMonotonicTime(Time::FromInternalValue(2000000));
+
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Check that durations are correct for a successful update where
+  // time has advanced 7 seconds on the wall clock and 4 seconds on
+  // the monotonic clock.
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+  fake_clock.SetWallclockTime(Time::FromInternalValue(8000000));
+  fake_clock.SetMonotonicTime(Time::FromInternalValue(6000000));
+  payload_state.UpdateSucceeded();
+  EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 7000000);
+  EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 4000000);
+
+  // Check that durations are reset when a new response comes in.
+  SetupPayloadStateWith2Urls("Hash8594", true, &payload_state, &response);
+  EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 0);
+  EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 0);
+
+  // Advance time a bit (10 secs), simulate download progress and
+  // check that durations are updated.
+  fake_clock.SetWallclockTime(Time::FromInternalValue(18000000));
+  fake_clock.SetMonotonicTime(Time::FromInternalValue(16000000));
+  payload_state.DownloadProgress(10);
+  EXPECT_EQ(payload_state.GetUpdateDuration().InMicroseconds(), 10000000);
+  EXPECT_EQ(payload_state.GetUpdateDurationUptime().InMicroseconds(), 10000000);
+
+  // Now simulate a reboot by resetting monotonic time (to 5000) and
+  // creating a new PayloadState object and check that we load the
+  // durations correctly (e.g. they are the same as before).
+  fake_clock.SetMonotonicTime(Time::FromInternalValue(5000));
+  PayloadState payload_state2;
+  EXPECT_TRUE(payload_state2.Initialize(&fake_system_state));
+  EXPECT_EQ(payload_state2.GetUpdateDuration().InMicroseconds(), 10000000);
+  EXPECT_EQ(payload_state2.GetUpdateDurationUptime().InMicroseconds(),
+            10000000);
+
+  // Advance wall-clock by 7 seconds and monotonic clock by 6 seconds
+  // and check that the durations are increased accordingly.
+  fake_clock.SetWallclockTime(Time::FromInternalValue(25000000));
+  fake_clock.SetMonotonicTime(Time::FromInternalValue(6005000));
+  payload_state2.UpdateSucceeded();
+  EXPECT_EQ(payload_state2.GetUpdateDuration().InMicroseconds(), 17000000);
+  EXPECT_EQ(payload_state2.GetUpdateDurationUptime().InMicroseconds(),
+            16000000);
+}
+
+TEST(PayloadStateTest, RebootAfterSuccessfulUpdateTest) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+
+  // Set the clock to a well-known time (t = 30 seconds).
+  fake_clock.SetWallclockTime(Time::FromInternalValue(
+      30 * Time::kMicrosecondsPerSecond));
+
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Make the update succeed.
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+  payload_state.UpdateSucceeded();
+
+  // Check that the marker was written.
+  EXPECT_TRUE(fake_prefs.Exists(kPrefsSystemUpdatedMarker));
+
+  // Now simulate a reboot and set the wallclock time to a later point
+  // (t = 500 seconds). We do this by using a new PayloadState object
+  // and checking that it emits the right UMA metric with the right
+  // value.
+  fake_clock.SetWallclockTime(Time::FromInternalValue(
+      500 * Time::kMicrosecondsPerSecond));
+  PayloadState payload_state2;
+  EXPECT_TRUE(payload_state2.Initialize(&fake_system_state));
+
+  // Expect 500 - 30 seconds = 470 seconds ~= 7 min 50 sec
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricTimeToRebootMinutes,
+      7, _, _, _));
+  fake_system_state.set_system_rebooted(true);
+
+  payload_state2.UpdateEngineStarted();
+
+  // Check that the marker was nuked.
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsSystemUpdatedMarker));
+}
+
+TEST(PayloadStateTest, RestartAfterCrash) {
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  NiceMock<MockPrefs>* prefs = fake_system_state.mock_prefs();
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Only the |kPrefsAttemptInProgress| state variable should be read.
+  EXPECT_CALL(*prefs, Exists(_)).Times(0);
+  EXPECT_CALL(*prefs, SetString(_, _)).Times(0);
+  EXPECT_CALL(*prefs, SetInt64(_, _)).Times(0);
+  EXPECT_CALL(*prefs, SetBoolean(_, _)).Times(0);
+  EXPECT_CALL(*prefs, GetString(_, _)).Times(0);
+  EXPECT_CALL(*prefs, GetInt64(_, _)).Times(0);
+  EXPECT_CALL(*prefs, GetBoolean(_, _)).Times(0);
+  EXPECT_CALL(*prefs, GetBoolean(kPrefsAttemptInProgress, _));
+
+  // No metrics are reported after a crash.
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(),
+              SendToUMA(_, _, _, _, _)).Times(0);
+
+  // Simulate an update_engine restart without a reboot.
+  fake_system_state.set_system_rebooted(false);
+
+  payload_state.UpdateEngineStarted();
+}
+
+TEST(PayloadStateTest, AbnormalTerminationAttemptMetricsNoReporting) {
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  // If there's no marker at startup, ensure we don't report a metric.
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(),
+      SendEnumToUMA(
+          metrics::kMetricAttemptResult,
+          static_cast<int>(metrics::AttemptResult::kAbnormalTermination),
+          _)).Times(0);
+  payload_state.UpdateEngineStarted();
+}
+
+TEST(PayloadStateTest, AbnormalTerminationAttemptMetricsReported) {
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakePrefs fake_prefs;
+
+  // If we have a marker at startup, ensure it's reported and the
+  // marker is then cleared.
+  fake_system_state.set_prefs(&fake_prefs);
+  fake_prefs.SetBoolean(kPrefsAttemptInProgress, true);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(),
+      SendEnumToUMA(
+          metrics::kMetricAttemptResult,
+          static_cast<int>(metrics::AttemptResult::kAbnormalTermination),
+          _)).Times(1);
+  payload_state.UpdateEngineStarted();
+
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsAttemptInProgress));
+}
+
+TEST(PayloadStateTest, AbnormalTerminationAttemptMetricsClearedOnSucceess) {
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakePrefs fake_prefs;
+
+  // Make sure the marker is written and cleared during an attempt and
+  // also that we DO NOT emit the metric (since the attempt didn't end
+  // abnormally).
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(_, _, _, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(),
+      SendEnumToUMA(
+          metrics::kMetricAttemptResult,
+          static_cast<int>(metrics::AttemptResult::kAbnormalTermination),
+          _)).Times(0);
+
+  // Attempt not in progress, should be clear.
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsAttemptInProgress));
+
+  payload_state.UpdateRestarted();
+
+  // Attempt not in progress, should be set.
+  EXPECT_TRUE(fake_prefs.Exists(kPrefsAttemptInProgress));
+
+  payload_state.UpdateSucceeded();
+
+  // Attempt not in progress, should be clear.
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsAttemptInProgress));
+}
+
+TEST(PayloadStateTest, CandidateUrlsComputedCorrectly) {
+  OmahaResponse response;
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+
+  policy::MockDevicePolicy disable_http_policy;
+  fake_system_state.set_device_policy(&disable_http_policy);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  // Test with no device policy. Should default to allowing http.
+  EXPECT_CALL(disable_http_policy, GetHttpDownloadsEnabled(_))
+      .WillRepeatedly(Return(false));
+
+  // Set the first response.
+  SetupPayloadStateWith2Urls("Hash8433", true, &payload_state, &response);
+
+  // Check that we use the HTTP URL since there is no value set for allowing
+  // http.
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+
+  // Test with device policy not allowing http updates.
+  EXPECT_CALL(disable_http_policy, GetHttpDownloadsEnabled(_))
+      .WillRepeatedly(DoAll(SetArgumentPointee<0>(false), Return(true)));
+
+  // Reset state and set again.
+  SetupPayloadStateWith2Urls("Hash8433", false, &payload_state, &response);
+
+  // Check that we skip the HTTP URL and use only the HTTPS url.
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+
+  // Advance the URL index to 1 by faking an error.
+  ErrorCode error = ErrorCode::kDownloadMetadataSignatureMismatch;
+  payload_state.UpdateFailed(error);
+
+  // Check that we still skip the HTTP URL and use only the HTTPS url.
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlSwitchCount());
+
+  // Now, slightly change the response and set it again.
+  SetupPayloadStateWith2Urls("Hash2399", false, &payload_state, &response);
+
+  // Check that we still skip the HTTP URL and use only the HTTPS url.
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+
+  // Now, pretend that the HTTP policy is turned on. We want to make sure
+  // the new policy is honored.
+  policy::MockDevicePolicy enable_http_policy;
+  fake_system_state.set_device_policy(&enable_http_policy);
+  EXPECT_CALL(enable_http_policy, GetHttpDownloadsEnabled(_))
+      .WillRepeatedly(DoAll(SetArgumentPointee<0>(true), Return(true)));
+
+  // Now, set the same response using the same hash
+  // so that we can test that the state is reset not because of the
+  // hash but because of the policy change which results in candidate url
+  // list change.
+  SetupPayloadStateWith2Urls("Hash2399", true, &payload_state, &response);
+
+  // Check that we use the HTTP URL now and the failure count is reset.
+  EXPECT_EQ("http://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+
+  // Fake a failure and see if we're moving over to the HTTPS url and update
+  // the URL switch count properly.
+  payload_state.UpdateFailed(error);
+  EXPECT_EQ("https://test", payload_state.GetCurrentUrl());
+  EXPECT_EQ(1, payload_state.GetUrlSwitchCount());
+  EXPECT_EQ(0, payload_state.GetUrlFailureCount());
+}
+
+TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsDelta) {
+  OmahaResponse response;
+  response.is_delta_payload = true;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricAttemptPayloadType, kPayloadTypeDelta, kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricSuccessfulUpdatePayloadType, kPayloadTypeDelta,
+      kNumPayloadTypes));
+  payload_state.UpdateSucceeded();
+
+  // Mock the request to a request where the delta was disabled but Omaha sends
+  // a delta anyway and test again.
+  OmahaRequestParams params(&fake_system_state);
+  params.set_delta_okay(false);
+  fake_system_state.set_request_params(&params);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  payload_state.DownloadComplete();
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricAttemptPayloadType, kPayloadTypeDelta,
+      kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricSuccessfulUpdatePayloadType, kPayloadTypeDelta,
+      kNumPayloadTypes));
+  payload_state.UpdateSucceeded();
+}
+
+TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsForcedFull) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Mock the request to a request where the delta was disabled.
+  OmahaRequestParams params(&fake_system_state);
+  params.set_delta_okay(false);
+  fake_system_state.set_request_params(&params);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricAttemptPayloadType, kPayloadTypeForcedFull,
+      kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricSuccessfulUpdatePayloadType, kPayloadTypeForcedFull,
+      kNumPayloadTypes));
+  payload_state.UpdateSucceeded();
+}
+
+TEST(PayloadStateTest, PayloadTypeMetricWhenTypeIsFull) {
+  OmahaResponse response;
+  response.is_delta_payload = false;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash6437", true, &payload_state, &response);
+
+  // Mock the request to a request where the delta is enabled, although the
+  // result is full.
+  OmahaRequestParams params(&fake_system_state);
+  params.set_delta_okay(true);
+  fake_system_state.set_request_params(&params);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(_, _, _))
+    .Times(AnyNumber());
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricAttemptPayloadType, kPayloadTypeFull,
+      kNumPayloadTypes));
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendEnumToUMA(
+      metrics::kMetricSuccessfulUpdatePayloadType, kPayloadTypeFull,
+      kNumPayloadTypes));
+  payload_state.UpdateSucceeded();
+}
+
+TEST(PayloadStateTest, RebootAfterUpdateFailedMetric) {
+  FakeSystemState fake_system_state;
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakePrefs fake_prefs;
+  fake_system_state.set_prefs(&fake_prefs);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash3141", true, &payload_state, &response);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+  payload_state.UpdateSucceeded();
+  payload_state.ExpectRebootInNewVersion("Version:12345678");
+
+  // Reboot into the same environment to get an UMA metric with a value of 1.
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, 1, _, _, _));
+  payload_state.ReportFailedBootIfNeeded();
+  Mock::VerifyAndClearExpectations(fake_system_state.mock_metrics_lib());
+
+  // Simulate a second update and reboot into the same environment, this should
+  // send a value of 2.
+  payload_state.ExpectRebootInNewVersion("Version:12345678");
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, 2, _, _, _));
+  payload_state.ReportFailedBootIfNeeded();
+  Mock::VerifyAndClearExpectations(fake_system_state.mock_metrics_lib());
+
+  // Simulate a third failed reboot to new version, but this time for a
+  // different payload. This should send a value of 1 this time.
+  payload_state.ExpectRebootInNewVersion("Version:3141592");
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, 1, _, _, _));
+  payload_state.ReportFailedBootIfNeeded();
+  Mock::VerifyAndClearExpectations(fake_system_state.mock_metrics_lib());
+}
+
+TEST(PayloadStateTest, RebootAfterUpdateSucceed) {
+  FakeSystemState fake_system_state;
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakePrefs fake_prefs;
+  fake_system_state.set_prefs(&fake_prefs);
+
+  FakeBootControl* fake_boot_control = fake_system_state.fake_boot_control();
+  fake_boot_control->SetCurrentSlot(0);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash3141", true, &payload_state, &response);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+  payload_state.UpdateSucceeded();
+  payload_state.ExpectRebootInNewVersion("Version:12345678");
+
+  // Change the BootDevice to a different one, no metric should be sent.
+  fake_boot_control->SetCurrentSlot(1);
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, _, _, _, _))
+      .Times(0);
+  payload_state.ReportFailedBootIfNeeded();
+
+  // A second reboot in either partition should not send a metric.
+  payload_state.ReportFailedBootIfNeeded();
+  fake_boot_control->SetCurrentSlot(0);
+  payload_state.ReportFailedBootIfNeeded();
+}
+
+TEST(PayloadStateTest, RebootAfterCanceledUpdate) {
+  FakeSystemState fake_system_state;
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakePrefs fake_prefs;
+
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash3141", true, &payload_state, &response);
+
+  // Simulate a successful download and update.
+  payload_state.DownloadComplete();
+  payload_state.UpdateSucceeded();
+  payload_state.ExpectRebootInNewVersion("Version:12345678");
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, _, _, _, _))
+      .Times(0);
+
+  // Cancel the applied update.
+  payload_state.ResetUpdateStatus();
+
+  // Simulate a reboot.
+  payload_state.ReportFailedBootIfNeeded();
+}
+
+TEST(PayloadStateTest, UpdateSuccessWithWipedPrefs) {
+  FakeSystemState fake_system_state;
+  PayloadState payload_state;
+  FakePrefs fake_prefs;
+
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+
+  EXPECT_CALL(*fake_system_state.mock_metrics_lib(), SendToUMA(
+      metrics::kMetricFailedUpdateCount, _, _, _, _))
+      .Times(0);
+
+  // Simulate a reboot in this environment.
+  payload_state.ReportFailedBootIfNeeded();
+}
+
+TEST(PayloadStateTest, DisallowP2PAfterTooManyAttempts) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakePrefs fake_prefs;
+  fake_system_state.set_prefs(&fake_prefs);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // Should allow exactly kMaxP2PAttempts...
+  for (int n = 0; n < kMaxP2PAttempts; n++) {
+    payload_state.P2PNewAttempt();
+    EXPECT_TRUE(payload_state.P2PAttemptAllowed());
+  }
+  // ... but not more than that.
+  payload_state.P2PNewAttempt();
+  EXPECT_FALSE(payload_state.P2PAttemptAllowed());
+}
+
+TEST(PayloadStateTest, DisallowP2PAfterDeadline) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // Set the clock to 1 second.
+  Time epoch = Time::FromInternalValue(1000000);
+  fake_clock.SetWallclockTime(epoch);
+
+  // Do an attempt - this will set the timestamp.
+  payload_state.P2PNewAttempt();
+
+  // Check that the timestamp equals what we just set.
+  EXPECT_EQ(epoch, payload_state.GetP2PFirstAttemptTimestamp());
+
+  // Time hasn't advanced - this should work.
+  EXPECT_TRUE(payload_state.P2PAttemptAllowed());
+
+  // Set clock to half the deadline - this should work.
+  fake_clock.SetWallclockTime(epoch +
+      TimeDelta::FromSeconds(kMaxP2PAttemptTimeSeconds) / 2);
+  EXPECT_TRUE(payload_state.P2PAttemptAllowed());
+
+  // Check that the first attempt timestamp hasn't changed just
+  // because the wall-clock time changed.
+  EXPECT_EQ(epoch, payload_state.GetP2PFirstAttemptTimestamp());
+
+  // Set clock to _just_ before the deadline - this should work.
+  fake_clock.SetWallclockTime(epoch +
+      TimeDelta::FromSeconds(kMaxP2PAttemptTimeSeconds - 1));
+  EXPECT_TRUE(payload_state.P2PAttemptAllowed());
+
+  // Set clock to _just_ after the deadline - this should not work.
+  fake_clock.SetWallclockTime(epoch +
+      TimeDelta::FromSeconds(kMaxP2PAttemptTimeSeconds + 1));
+  EXPECT_FALSE(payload_state.P2PAttemptAllowed());
+}
+
+TEST(PayloadStateTest, P2PStateVarsInitialValue) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakePrefs fake_prefs;
+
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  Time null_time = Time();
+  EXPECT_EQ(null_time, payload_state.GetP2PFirstAttemptTimestamp());
+  EXPECT_EQ(0, payload_state.GetP2PNumAttempts());
+}
+
+TEST(PayloadStateTest, P2PStateVarsArePersisted) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // Set the clock to something known.
+  Time time = Time::FromInternalValue(12345);
+  fake_clock.SetWallclockTime(time);
+
+  // New p2p attempt - as a side-effect this will update the p2p state vars.
+  payload_state.P2PNewAttempt();
+  EXPECT_EQ(1, payload_state.GetP2PNumAttempts());
+  EXPECT_EQ(time, payload_state.GetP2PFirstAttemptTimestamp());
+
+  // Now create a new PayloadState and check that it loads the state
+  // vars correctly.
+  PayloadState payload_state2;
+  EXPECT_TRUE(payload_state2.Initialize(&fake_system_state));
+  EXPECT_EQ(1, payload_state2.GetP2PNumAttempts());
+  EXPECT_EQ(time, payload_state2.GetP2PFirstAttemptTimestamp());
+}
+
+TEST(PayloadStateTest, P2PStateVarsAreClearedOnNewResponse) {
+  OmahaResponse response;
+  PayloadState payload_state;
+  FakeSystemState fake_system_state;
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+  fake_system_state.set_clock(&fake_clock);
+  fake_system_state.set_prefs(&fake_prefs);
+
+  EXPECT_TRUE(payload_state.Initialize(&fake_system_state));
+  SetupPayloadStateWith2Urls("Hash8593", true, &payload_state, &response);
+
+  // Set the clock to something known.
+  Time time = Time::FromInternalValue(12345);
+  fake_clock.SetWallclockTime(time);
+
+  // New p2p attempt - as a side-effect this will update the p2p state vars.
+  payload_state.P2PNewAttempt();
+  EXPECT_EQ(1, payload_state.GetP2PNumAttempts());
+  EXPECT_EQ(time, payload_state.GetP2PFirstAttemptTimestamp());
+
+  // Set a new response...
+  SetupPayloadStateWith2Urls("Hash9904", true, &payload_state, &response);
+
+  // ... and check that it clears the P2P state vars.
+  Time null_time = Time();
+  EXPECT_EQ(0, payload_state.GetP2PNumAttempts());
+  EXPECT_EQ(null_time, payload_state.GetP2PFirstAttemptTimestamp());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/proxy_resolver.cc b/proxy_resolver.cc
new file mode 100644
index 0000000..abd6f76
--- /dev/null
+++ b/proxy_resolver.cc
@@ -0,0 +1,66 @@
+//
+// Copyright (C) 2010 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 "update_engine/proxy_resolver.h"
+
+#include <base/bind.h>
+#include <base/location.h>
+
+using brillo::MessageLoop;
+using std::deque;
+using std::string;
+
+namespace chromeos_update_engine {
+
+const char kNoProxy[] = "direct://";
+
+DirectProxyResolver::~DirectProxyResolver() {
+  if (idle_callback_id_ != MessageLoop::kTaskIdNull) {
+    // The DirectProxyResolver is instantiated as part of the UpdateAttempter
+    // which is also instantiated by default by the FakeSystemState, even when
+    // it is not used. We check the manage_shares_id_ before calling the
+    // MessageLoop::current() since the unit test using a FakeSystemState may
+    // have not define a MessageLoop for the current thread.
+    MessageLoop::current()->CancelTask(idle_callback_id_);
+    idle_callback_id_ = MessageLoop::kTaskIdNull;
+  }
+}
+
+bool DirectProxyResolver::GetProxiesForUrl(const string& url,
+                                           ProxiesResolvedFn callback,
+                                           void* data) {
+  idle_callback_id_ = MessageLoop::current()->PostTask(
+      FROM_HERE,
+      base::Bind(
+            &DirectProxyResolver::ReturnCallback,
+            base::Unretained(this),
+            callback,
+            data));
+  return true;
+}
+
+void DirectProxyResolver::ReturnCallback(ProxiesResolvedFn callback,
+                                         void* data) {
+  idle_callback_id_ = MessageLoop::kTaskIdNull;
+
+  // Initialize proxy pool with as many proxies as indicated (all identical).
+  deque<string> proxies(num_proxies_, kNoProxy);
+
+  (*callback)(proxies, data);
+}
+
+
+}  // namespace chromeos_update_engine
diff --git a/proxy_resolver.h b/proxy_resolver.h
new file mode 100644
index 0000000..2c8824f
--- /dev/null
+++ b/proxy_resolver.h
@@ -0,0 +1,88 @@
+//
+// Copyright (C) 2010 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.
+//
+
+#ifndef UPDATE_ENGINE_PROXY_RESOLVER_H_
+#define UPDATE_ENGINE_PROXY_RESOLVER_H_
+
+#include <deque>
+#include <string>
+
+#include <base/logging.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/utils.h"
+
+namespace chromeos_update_engine {
+
+extern const char kNoProxy[];
+
+// Callback for a call to GetProxiesForUrl().
+// Resultant proxies are in |out_proxy|. Each will be in one of the
+// following forms:
+// http://<host>[:<port>] - HTTP proxy
+// socks{4,5}://<host>[:<port>] - SOCKS4/5 proxy
+// kNoProxy - no proxy
+typedef void (*ProxiesResolvedFn)(const std::deque<std::string>& proxies,
+                                  void* data);
+
+class ProxyResolver {
+ public:
+  ProxyResolver() {}
+  virtual ~ProxyResolver() {}
+
+  // Finds proxies for the given URL and returns them via the callback.
+  // |data| will be passed to the callback.
+  // Returns true on success.
+  virtual bool GetProxiesForUrl(const std::string& url,
+                                ProxiesResolvedFn callback,
+                                void* data) = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ProxyResolver);
+};
+
+// Always says to not use a proxy
+class DirectProxyResolver : public ProxyResolver {
+ public:
+  DirectProxyResolver() = default;
+  ~DirectProxyResolver() override;
+  bool GetProxiesForUrl(const std::string& url,
+                        ProxiesResolvedFn callback,
+                        void* data) override;
+
+  // Set the number of direct (non-) proxies to be returned by resolver.
+  // The default value is 1; higher numbers are currently used in testing.
+  inline void set_num_proxies(size_t num_proxies) {
+    num_proxies_ = num_proxies;
+  }
+
+ private:
+  // The ID of the main loop callback.
+  brillo::MessageLoop::TaskId idle_callback_id_{
+      brillo::MessageLoop::kTaskIdNull};
+
+  // Number of direct proxies to return on resolved list; currently used for
+  // testing.
+  size_t num_proxies_{1};
+
+  // The MainLoop callback, from here we return to the client.
+  void ReturnCallback(ProxiesResolvedFn callback, void* data);
+  DISALLOW_COPY_AND_ASSIGN(DirectProxyResolver);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_PROXY_RESOLVER_H_
diff --git a/real_system_state.cc b/real_system_state.cc
new file mode 100644
index 0000000..3a90292
--- /dev/null
+++ b/real_system_state.cc
@@ -0,0 +1,151 @@
+//
+// Copyright (C) 2012 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 "update_engine/real_system_state.h"
+
+#include <base/files/file_util.h>
+#include <base/time/time.h>
+#include <brillo/make_unique_ptr.h>
+
+#include "update_engine/common/boot_control.h"
+#include "update_engine/common/boot_control_stub.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/state_factory.h"
+
+namespace chromeos_update_engine {
+
+RealSystemState::RealSystemState(const scoped_refptr<dbus::Bus>& bus)
+    : debugd_proxy_(bus),
+      power_manager_proxy_(bus),
+      session_manager_proxy_(bus),
+      shill_proxy_(bus),
+      libcros_proxy_(bus) {
+}
+
+bool RealSystemState::Initialize() {
+  metrics_lib_.Init();
+
+  boot_control_ = boot_control::CreateBootControl();
+  if (!boot_control_) {
+    LOG(WARNING) << "Unable to create BootControl instance, using stub "
+                 << "instead. All update attempts will fail.";
+    boot_control_ = brillo::make_unique_ptr(new BootControlStub());
+  }
+
+  hardware_ = hardware::CreateHardware();
+  if (!hardware_) {
+    LOG(ERROR) << "Error intializing the HardwareInterface.";
+    return false;
+  }
+
+  LOG_IF(INFO, !hardware_->IsNormalBootMode()) << "Booted in dev mode.";
+  LOG_IF(INFO, !hardware_->IsOfficialBuild()) << "Booted non-official build.";
+
+  if (!shill_proxy_.Init()) {
+    LOG(ERROR) << "Failed to initialize shill proxy.";
+    return false;
+  }
+
+  // Initialize standard and powerwash-safe prefs.
+  base::FilePath non_volatile_path;
+  // TODO(deymo): Fall back to in-memory prefs if there's no physical directory
+  // available.
+  if (!hardware_->GetNonVolatileDirectory(&non_volatile_path)) {
+    LOG(ERROR) << "Failed to get a non-volatile directory.";
+    return false;
+  }
+  Prefs* prefs;
+  prefs_.reset(prefs = new Prefs());
+  if (!prefs->Init(non_volatile_path.Append(kPrefsSubDirectory))) {
+    LOG(ERROR) << "Failed to initialize preferences.";
+    return false;
+  }
+
+  base::FilePath powerwash_safe_path;
+  if (!hardware_->GetPowerwashSafeDirectory(&powerwash_safe_path)) {
+    // TODO(deymo): Fall-back to in-memory prefs if there's no powerwash-safe
+    // directory, or disable powerwash feature.
+    powerwash_safe_path = non_volatile_path.Append("powerwash-safe");
+    LOG(WARNING) << "No powerwash-safe directory, using non-volatile one.";
+  }
+  powerwash_safe_prefs_.reset(prefs = new Prefs());
+  if (!prefs->Init(
+          powerwash_safe_path.Append(kPowerwashSafePrefsSubDirectory))) {
+    LOG(ERROR) << "Failed to initialize powerwash preferences.";
+    return false;
+  }
+
+  // Check the system rebooted marker file.
+  std::string boot_id;
+  if (utils::GetBootId(&boot_id)) {
+    std::string prev_boot_id;
+    system_rebooted_ = (!prefs_->GetString(kPrefsBootId, &prev_boot_id) ||
+                        prev_boot_id != boot_id);
+    prefs_->SetString(kPrefsBootId, boot_id);
+  } else {
+    LOG(WARNING) << "Couldn't detect the bootid, assuming system was rebooted.";
+    system_rebooted_ = true;
+  }
+
+  // Initialize the OmahaRequestParams with the default settings. These settings
+  // will be re-initialized before every request using the actual request
+  // options. This initialization here pre-loads current channel and version, so
+  // the DBus service can access it.
+  if (!request_params_.Init("", "", false)) {
+    LOG(WARNING) << "Ignoring OmahaRequestParams initialization error. Some "
+                    "features might not work properly.";
+  }
+
+  certificate_checker_.reset(
+      new CertificateChecker(prefs_.get(), &openssl_wrapper_));
+  certificate_checker_->Init();
+
+  // Initialize the UpdateAttempter before the UpdateManager.
+  update_attempter_.reset(
+      new UpdateAttempter(this, certificate_checker_.get(), &libcros_proxy_,
+                          &debugd_proxy_));
+  update_attempter_->Init();
+
+  // Initialize the Update Manager using the default state factory.
+  chromeos_update_manager::State* um_state =
+      chromeos_update_manager::DefaultStateFactory(
+          &policy_provider_, &shill_proxy_, &session_manager_proxy_, this);
+  if (!um_state) {
+    LOG(ERROR) << "Failed to initialize the Update Manager.";
+    return false;
+  }
+  update_manager_.reset(
+      new chromeos_update_manager::UpdateManager(
+          &clock_, base::TimeDelta::FromSeconds(5),
+          base::TimeDelta::FromHours(12), um_state));
+
+  // The P2P Manager depends on the Update Manager for its initialization.
+  p2p_manager_.reset(P2PManager::Construct(
+          nullptr, &clock_, update_manager_.get(), "cros_au",
+          kMaxP2PFilesToKeep, base::TimeDelta::FromDays(kMaxP2PFileAgeDays)));
+
+  if (!payload_state_.Initialize(this)) {
+    LOG(ERROR) << "Failed to initialize the payload state object.";
+    return false;
+  }
+
+  // All is well. Initialization successful.
+  return true;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/real_system_state.h b/real_system_state.h
new file mode 100644
index 0000000..8ca1abc
--- /dev/null
+++ b/real_system_state.h
@@ -0,0 +1,173 @@
+//
+// Copyright (C) 2013 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.
+//
+
+#ifndef UPDATE_ENGINE_REAL_SYSTEM_STATE_H_
+#define UPDATE_ENGINE_REAL_SYSTEM_STATE_H_
+
+#include "update_engine/system_state.h"
+
+#include <memory>
+
+#include <debugd/dbus-proxies.h>
+#include <metrics/metrics_library.h>
+#include <policy/device_policy.h>
+#include <power_manager/dbus-proxies.h>
+#include <session_manager/dbus-proxies.h>
+
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/common/clock.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/connection_manager.h"
+#include "update_engine/p2p_manager.h"
+#include "update_engine/payload_state.h"
+#include "update_engine/shill_proxy.h"
+#include "update_engine/update_attempter.h"
+#include "update_engine/update_manager/update_manager.h"
+
+namespace chromeos_update_engine {
+
+// A real implementation of the SystemStateInterface which is
+// used by the actual product code.
+class RealSystemState : public SystemState {
+ public:
+  // Constructs all system objects that do not require separate initialization;
+  // see Initialize() below for the remaining ones.
+  explicit RealSystemState(const scoped_refptr<dbus::Bus>& bus);
+
+  // Initializes and sets systems objects that require an initialization
+  // separately from construction. Returns |true| on success.
+  bool Initialize();
+
+  inline void set_device_policy(
+      const policy::DevicePolicy* device_policy) override {
+    device_policy_ = device_policy;
+  }
+
+  inline const policy::DevicePolicy* device_policy() override {
+    return device_policy_;
+  }
+
+  inline BootControlInterface* boot_control() override {
+    return boot_control_.get();
+  }
+
+  inline ClockInterface* clock() override { return &clock_; }
+
+  inline ConnectionManagerInterface* connection_manager() override {
+    return &connection_manager_;
+  }
+
+  inline HardwareInterface* hardware() override { return hardware_.get(); }
+
+  inline MetricsLibraryInterface* metrics_lib() override {
+    return &metrics_lib_;
+  }
+
+  inline PrefsInterface* prefs() override { return prefs_.get(); }
+
+  inline PrefsInterface* powerwash_safe_prefs() override {
+    return powerwash_safe_prefs_.get();
+  }
+
+  inline PayloadStateInterface* payload_state() override {
+    return &payload_state_;
+  }
+
+  inline UpdateAttempter* update_attempter() override {
+    return update_attempter_.get();
+  }
+
+  inline OmahaRequestParams* request_params() override {
+    return &request_params_;
+  }
+
+  inline P2PManager* p2p_manager() override { return p2p_manager_.get(); }
+
+  inline chromeos_update_manager::UpdateManager* update_manager() override {
+    return update_manager_.get();
+  }
+
+  inline org::chromium::PowerManagerProxyInterface* power_manager_proxy()
+      override {
+    return &power_manager_proxy_;
+  }
+
+  inline bool system_rebooted() override { return system_rebooted_; }
+
+ private:
+  // Real DBus proxies using the DBus connection.
+  org::chromium::debugdProxy debugd_proxy_;
+  org::chromium::PowerManagerProxy power_manager_proxy_;
+  org::chromium::SessionManagerInterfaceProxy session_manager_proxy_;
+  ShillProxy shill_proxy_;
+  LibCrosProxy libcros_proxy_;
+
+  // Interface for the clock.
+  std::unique_ptr<BootControlInterface> boot_control_;
+
+  // Interface for the clock.
+  Clock clock_;
+
+  // The latest device policy object from the policy provider.
+  const policy::DevicePolicy* device_policy_{nullptr};
+
+  // The connection manager object that makes download decisions depending on
+  // the current type of connection.
+  ConnectionManager connection_manager_{&shill_proxy_, this};
+
+  // Interface for the hardware functions.
+  std::unique_ptr<HardwareInterface> hardware_;
+
+  // The Metrics Library interface for reporting UMA stats.
+  MetricsLibrary metrics_lib_;
+
+  // Interface for persisted store.
+  std::unique_ptr<PrefsInterface> prefs_;
+
+  // Interface for persisted store that persists across powerwashes.
+  std::unique_ptr<PrefsInterface> powerwash_safe_prefs_;
+
+  // All state pertaining to payload state such as response, URL, backoff
+  // states.
+  PayloadState payload_state_;
+
+  // OpenSSLWrapper and CertificateChecker used for checking SSL certificates.
+  OpenSSLWrapper openssl_wrapper_;
+  std::unique_ptr<CertificateChecker> certificate_checker_;
+
+  // Pointer to the update attempter object.
+  std::unique_ptr<UpdateAttempter> update_attempter_;
+
+  // Common parameters for all Omaha requests.
+  OmahaRequestParams request_params_{this};
+
+  std::unique_ptr<P2PManager> p2p_manager_;
+
+  std::unique_ptr<chromeos_update_manager::UpdateManager> update_manager_;
+
+  policy::PolicyProvider policy_provider_;
+
+  // If true, this is the first instance of the update engine since the system
+  // rebooted. Important for tracking whether you are running instance of the
+  // update engine on first boot or due to a crash/restart.
+  bool system_rebooted_{false};
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_REAL_SYSTEM_STATE_H_
diff --git a/run_unittests b/run_unittests
new file mode 100755
index 0000000..f07078d
--- /dev/null
+++ b/run_unittests
@@ -0,0 +1,35 @@
+#!/bin/bash
+
+#
+# Copyright (C) 2012 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.
+#
+
+# Runs the update engine unit tests, including both userland and run-as-root
+# tests.
+
+if [ ! -e ./update_engine_unittests ]; then
+  echo 'Error: unit test binary missing' >&2
+  exit 1
+fi
+
+user_pass=0
+./update_engine_unittests --gtest_filter='-*.RunAsRoot*' && user_pass=1
+root_pass=0
+sudo ./update_engine_unittests --gtest_filter='*.RunAsRoot*' && root_pass=1
+
+echo -n "User tests: " && [ $user_pass == 1 ] && echo "PASSED" || echo "FAILED"
+echo -n "Root tests: " && [ $root_pass == 1 ] && echo "PASSED" || echo "FAILED"
+
+exit $((2 - user_pass - root_pass))
diff --git a/sample_images/generate_images.sh b/sample_images/generate_images.sh
new file mode 100755
index 0000000..70fc14b
--- /dev/null
+++ b/sample_images/generate_images.sh
@@ -0,0 +1,189 @@
+#!/bin/bash
+
+#
+# Copyright (C) 2015 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.
+#
+
+# This script generates some sample images used in unittests and packages them
+# in the sample_images.tar.bz2 file. The list of generated images and their
+# options are described in the main() function. You need to manually run this
+# script to update the generated images whenever you modify this script.
+
+set -e
+
+# cleanup <path>
+# Unmount and remove the mountpoint <path>
+cleanup() {
+  if ! sudo umount "$1" 2>/dev/null; then
+    if mountpoint -q "$1"; then
+      sync && sudo umount "$1"
+    fi
+  fi
+  rmdir "$1"
+}
+
+# add_files_default <mntdir> <block_size>
+# Add several test files to the image mounted in <mntdir>.
+add_files_default() {
+  local mntdir="$1"
+  local block_size="$2"
+
+  ### Generate the files used in unittest with descriptive names.
+  sudo touch "${mntdir}"/empty-file
+
+  # regular: Regular files.
+  echo "small file" | sudo dd of="${mntdir}"/regular-small status=none
+  dd if=/dev/zero bs=1024 count=16 status=none | tr '\0' '\141' |
+    sudo dd of="${mntdir}"/regular-16k status=none
+  sudo dd if=/dev/zero of="${mntdir}"/regular-32k-zeros bs=1024 count=16 \
+    status=none
+
+  echo "with net_cap" | sudo dd of="${mntdir}"/regular-with_net_cap status=none
+  sudo setcap cap_net_raw=ep "${mntdir}"/regular-with_net_cap
+
+  # sparse_empty: Files with no data blocks at all (only sparse holes).
+  sudo truncate --size=10240 "${mntdir}"/sparse_empty-10k
+  sudo truncate --size=$(( block_size * 2 )) "${mntdir}"/sparse_empty-2blocks
+
+  # sparse: Files with some data blocks but also sparse holes.
+  echo -n "foo" |
+    sudo dd of="${mntdir}"/sparse-16k-last_block bs=1 \
+      seek=$(( 16 * 1024 - 3)) status=none
+
+  # ext2 inodes have 12 direct blocks, one indirect, one double indirect and
+  # one triple indirect. 10000 should be enough to have an indirect and double
+  # indirect block.
+  echo -n "foo" |
+    sudo dd of="${mntdir}"/sparse-10000blocks bs=1 \
+      seek=$(( block_size * 10000 )) status=none
+
+  sudo truncate --size=16384 "${mntdir}"/sparse-16k-first_block
+  echo "first block" | sudo dd of="${mntdir}"/sparse-16k-first_block status=none
+
+  sudo truncate --size=16384 "${mntdir}"/sparse-16k-holes
+  echo "a" | sudo dd of="${mntdir}"/sparse-16k-holes bs=1 seek=100 status=none
+  echo "b" | sudo dd of="${mntdir}"/sparse-16k-holes bs=1 seek=10000 status=none
+
+  # link: symlinks and hardlinks.
+  sudo ln -s "broken-link" "${mntdir}"/link-short_symlink
+  sudo ln -s $(dd if=/dev/zero bs=256 count=1 status=none | tr '\0' '\141') \
+    "${mntdir}"/link-long_symlink
+  sudo ln "${mntdir}"/regular-16k "${mntdir}"/link-hard-regular-16k
+
+  # Directories.
+  sudo mkdir -p "${mntdir}"/dir1/dir2/dir1
+  echo "foo" | sudo tee "${mntdir}"/dir1/dir2/file >/dev/null
+  echo "bar" | sudo tee "${mntdir}"/dir1/file >/dev/null
+
+  # removed: removed files that should not be listed.
+  echo "We will remove this file so it's contents will be somewhere in the " \
+    "empty space data but it won't be all zeros." |
+    sudo dd of="${mntdir}"/removed conv=fsync status=none
+  sudo rm "${mntdir}"/removed
+}
+
+# add_files_ue_settings <mntdir> <block_size>
+# Add the update_engine.conf settings file. This file contains the
+add_files_ue_settings() {
+  local mntdir="$1"
+
+  sudo mkdir -p "${mntdir}"/etc >/dev/null
+  sudo tee "${mntdir}"/etc/update_engine.conf >/dev/null <<EOF
+PAYLOAD_MINOR_VERSION=1234
+EOF
+  # Example of a real lsb-release file released on link stable.
+  sudo tee "${mntdir}"/etc/lsb-release >/dev/null <<EOF
+CHROMEOS_AUSERVER=https://tools.google.com/service/update2
+CHROMEOS_BOARD_APPID={F26D159B-52A3-491A-AE25-B23670A66B32}
+CHROMEOS_CANARY_APPID={90F229CE-83E2-4FAF-8479-E368A34938B1}
+CHROMEOS_DEVSERVER=
+CHROMEOS_RELEASE_APPID={F26D159B-52A3-491A-AE25-B23670A66B32}
+CHROMEOS_RELEASE_BOARD=link-signed-mp-v4keys
+CHROMEOS_RELEASE_BRANCH_NUMBER=63
+CHROMEOS_RELEASE_BUILD_NUMBER=6946
+CHROMEOS_RELEASE_BUILD_TYPE=Official Build
+CHROMEOS_RELEASE_CHROME_MILESTONE=43
+CHROMEOS_RELEASE_DESCRIPTION=6946.63.0 (Official Build) stable-channel link
+CHROMEOS_RELEASE_NAME=Chrome OS
+CHROMEOS_RELEASE_PATCH_NUMBER=0
+CHROMEOS_RELEASE_TRACK=stable-channel
+CHROMEOS_RELEASE_VERSION=6946.63.0
+GOOGLE_RELEASE=6946.63.0
+EOF
+}
+
+# generate_fs <filename> <kind> <size> [block_size] [block_groups]
+generate_fs() {
+  local filename="$1"
+  local kind="$2"
+  local size="$3"
+  local block_size="${4:-4096}"
+  local block_groups="${5:-}"
+
+  local mkfs_opts=( -q -F -b "${block_size}" -L "ROOT-TEST" -t ext2 )
+  if [[ -n "${block_groups}" ]]; then
+    mkfs_opts+=( -G "${block_groups}" )
+  fi
+
+  local mntdir=$(mktemp --tmpdir -d generate_ext2.XXXXXX)
+  trap 'cleanup "${mntdir}"; rm -f "${filename}"' INT TERM EXIT
+
+  # Cleanup old image.
+  if [[ -e "${filename}" ]]; then
+    rm -f "${filename}"
+  fi
+  truncate --size="${size}" "${filename}"
+
+  mkfs.ext2 "${mkfs_opts[@]}" "${filename}"
+  sudo mount "${filename}" "${mntdir}" -o loop
+
+  case "${kind}" in
+    ue_settings)
+      add_files_ue_settings "${mntdir}" "${block_size}"
+      ;;
+    default)
+      add_files_default "${mntdir}" "${block_size}"
+      ;;
+  esac
+
+  cleanup "${mntdir}"
+  trap - INT TERM EXIT
+}
+
+OUTPUT_DIR=$(dirname "$0")
+IMAGES=()
+
+# generate_image <image_name> [<image args> ...]
+generate_image() {
+  echo "Generating image $1.img"
+  IMAGES+=( "$1.img" )
+  generate_fs "${OUTPUT_DIR}/$1.img" "${@:2}"
+}
+
+main() {
+  # Add more sample images here.
+  generate_image disk_ext2_1k default 16777216 1024
+  generate_image disk_ext2_4k default 16777216 4096
+  generate_image disk_ext2_ue_settings ue_settings 16777216 4096
+
+  # Generate the tarball and delete temporary images.
+  echo "Packing tar file sample_images.tar.bz2"
+  tar -jcf "${OUTPUT_DIR}/sample_images.tar.bz2" -C "${OUTPUT_DIR}" \
+    "${IMAGES[@]}"
+  cd "${OUTPUT_DIR}"
+  rm "${IMAGES[@]}"
+}
+
+main
diff --git a/sample_images/sample_images.tar.bz2 b/sample_images/sample_images.tar.bz2
new file mode 100644
index 0000000..0982271
--- /dev/null
+++ b/sample_images/sample_images.tar.bz2
Binary files differ
diff --git a/sample_omaha_v3_response.xml b/sample_omaha_v3_response.xml
new file mode 100644
index 0000000..abba523
--- /dev/null
+++ b/sample_omaha_v3_response.xml
@@ -0,0 +1,19 @@
+<response protocol="3.0" server="prod">
+  <daystart elapsed_seconds="56652"/>
+  <app appid="{90f229ce-83e2-4faf-8479-e368a34938b1}" status="ok">
+    <updatecheck status="ok">
+      <urls>
+        <url codebase="https://storage.googleapis.com/chromeos-releases-public/canary-channel/canary-channel/3095.0.0/"/>
+      </urls>
+      <manifest version="3095.0.0">
+        <packages>
+          <package hash="HVOmp67vBjPdvpWmOC2Uw4UDwsc=" name="chromeos_3095.0.0_x86-zgb_canary-channel_full_mp-v2.bin-df37843370ddf1e3819a2afeaa934faa.signed" required="true" size="400752559"/>
+        </packages>
+        <actions>
+          <action event="update" run="chromeos_3095.0.0_x86-zgb_canary-channel_full_mp-v2.bin-df37843370ddf1e3819a2afeaa934faa.signed"/>
+          <action ChromeOSVersion="3095.0.0" ChromeVersion="24.0.1307.0" IsDelta="true" IsDeltaPayload="false" MaxDaysToScatter="14" MetadataSignatureRsa="xXrO/LahHlKk3YmqEf1qE0PN587Sc2IJV+FN7J7x1h49waNQIy/QwYO4LaOySgETe5JZXtkAEzzqakfJwxQ2pVfzj1GkExwjd5LTn1He2GvA73B8fKbS4bfP7dbUFwD5039xCwf1U2gezFViOiOPiVURx/pEsdhv+Cqx/3HbjIuj5au2dooSyDxLC5AnODzAKyYfAcjMuiLON+9SqmctJW+VjzdY9SbJAnkH2qqVjFyBKAXsYT+hOTIJ3MJpg8OSVxMMtGB99PxbOJ52F37d2Y5Fws/AUkNnNEsan/WRJA1kuWoS6rpeR8JQYuVhLiK2u/KpOcvMVRw3Q2VUxtcAGw==" MetadataSize="58315" event="postinstall" sha256="DIAVxoI+8NpsudUawOA5U92VHlaxQBS3ejN4EPM6T2A="/>
+        </actions>
+      </manifest>
+    </updatecheck>
+  </app>
+</response>
diff --git a/shill_proxy.cc b/shill_proxy.cc
new file mode 100644
index 0000000..1c050b4
--- /dev/null
+++ b/shill_proxy.cc
@@ -0,0 +1,43 @@
+//
+// Copyright (C) 2015 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 "update_engine/shill_proxy.h"
+
+using org::chromium::flimflam::ManagerProxy;
+using org::chromium::flimflam::ManagerProxyInterface;
+using org::chromium::flimflam::ServiceProxy;
+using org::chromium::flimflam::ServiceProxyInterface;
+
+namespace chromeos_update_engine {
+
+ShillProxy::ShillProxy(const scoped_refptr<dbus::Bus>& bus) : bus_(bus) {}
+
+bool ShillProxy::Init() {
+  manager_proxy_.reset(new ManagerProxy(bus_));
+  return true;
+}
+
+ManagerProxyInterface* ShillProxy::GetManagerProxy() {
+  return manager_proxy_.get();
+}
+
+std::unique_ptr<ServiceProxyInterface> ShillProxy::GetServiceForPath(
+    const dbus::ObjectPath& path) {
+  DCHECK(bus_.get());
+  return std::unique_ptr<ServiceProxyInterface>(new ServiceProxy(bus_, path));
+}
+
+}  // namespace chromeos_update_engine
diff --git a/shill_proxy.h b/shill_proxy.h
new file mode 100644
index 0000000..6d545f6
--- /dev/null
+++ b/shill_proxy.h
@@ -0,0 +1,58 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_SHILL_PROXY_H_
+#define UPDATE_ENGINE_SHILL_PROXY_H_
+
+#include <memory>
+#include <string>
+
+#include <base/macros.h>
+#include <dbus/bus.h>
+#include <dbus/object_path.h>
+#include <shill/dbus-proxies.h>
+
+#include "update_engine/shill_proxy_interface.h"
+
+namespace chromeos_update_engine {
+
+// This class implements the connection to shill using real DBus calls.
+class ShillProxy : public ShillProxyInterface {
+ public:
+  explicit ShillProxy(const scoped_refptr<dbus::Bus>& bus);
+  ~ShillProxy() override = default;
+
+  // Initializes the ShillProxy instance creating the manager proxy from the
+  // |bus_|.
+  bool Init();
+
+  // ShillProxyInterface overrides.
+  org::chromium::flimflam::ManagerProxyInterface* GetManagerProxy() override;
+  std::unique_ptr<org::chromium::flimflam::ServiceProxyInterface>
+  GetServiceForPath(const dbus::ObjectPath& path) override;
+
+ private:
+  // A reference to the main bus for creating new ServiceProxy instances.
+  scoped_refptr<dbus::Bus> bus_;
+  std::unique_ptr<org::chromium::flimflam::ManagerProxyInterface>
+      manager_proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(ShillProxy);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_SHILL_PROXY_H_
diff --git a/shill_proxy_interface.h b/shill_proxy_interface.h
new file mode 100644
index 0000000..5f6b44e
--- /dev/null
+++ b/shill_proxy_interface.h
@@ -0,0 +1,56 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_SHILL_PROXY_INTERFACE_H_
+#define UPDATE_ENGINE_SHILL_PROXY_INTERFACE_H_
+
+#include <memory>
+#include <string>
+
+#include <base/macros.h>
+#include <dbus/object_path.h>
+#include <shill/dbus-proxies.h>
+
+namespace chromeos_update_engine {
+
+// This class handles the DBus connection with shill daemon. The DBus interface
+// with shill requires to monitor or request the current service by interacting
+// with the org::chromium::flimflam::ManagerProxy and then request or monitor
+// properties on the selected org::chromium::flimflam::ServiceProxy. This class
+// provides a mockable way to access that.
+class ShillProxyInterface {
+ public:
+  virtual ~ShillProxyInterface() = default;
+
+  // Return the ManagerProxy instance of the shill daemon. The instance is owned
+  // by this ShillProxyInterface instance.
+  virtual org::chromium::flimflam::ManagerProxyInterface* GetManagerProxy() = 0;
+
+  // Return a ServiceProxy for the given path. The ownership of the returned
+  // instance is transferred to the caller.
+  virtual std::unique_ptr<org::chromium::flimflam::ServiceProxyInterface>
+  GetServiceForPath(const dbus::ObjectPath& path) = 0;
+
+ protected:
+  ShillProxyInterface() = default;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ShillProxyInterface);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_SHILL_PROXY_INTERFACE_H_
diff --git a/system_state.h b/system_state.h
new file mode 100644
index 0000000..2ba0272
--- /dev/null
+++ b/system_state.h
@@ -0,0 +1,122 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_SYSTEM_STATE_H_
+#define UPDATE_ENGINE_SYSTEM_STATE_H_
+
+namespace org {
+namespace chromium {
+class PowerManagerProxyInterface;
+}  // namespace chromium
+}  // namespace org
+
+class MetricsLibraryInterface;
+
+namespace chromeos_update_manager {
+
+class UpdateManager;
+
+}  // namespace chromeos_update_manager
+
+namespace policy {
+
+class DevicePolicy;
+
+}  // namespace policy
+
+namespace chromeos_update_engine {
+
+// SystemState is the root class within the update engine. So we should avoid
+// any circular references in header file inclusion. Hence forward-declaring
+// the required classes.
+class BootControlInterface;
+class ClockInterface;
+class ConnectionManagerInterface;
+class HardwareInterface;
+class OmahaRequestParams;
+class P2PManager;
+class PayloadStateInterface;
+class PrefsInterface;
+class UpdateAttempter;
+
+// An interface to global system context, including platform resources,
+// the current state of the system, high-level objects whose lifetime is same
+// as main, system interfaces, etc.
+// Carved out separately so it can be mocked for unit tests.
+// Currently it has only one method, but we should start migrating other
+// methods to use this as and when needed to unit test them.
+// TODO(jaysri): Consider renaming this to something like GlobalContext.
+class SystemState {
+ public:
+  // Destructs this object.
+  virtual ~SystemState() {}
+
+  // Sets or gets the latest device policy.
+  virtual void set_device_policy(const policy::DevicePolicy* device_policy) = 0;
+  virtual const policy::DevicePolicy* device_policy() = 0;
+
+  // Gets the interface object for the bootloader control interface.
+  virtual BootControlInterface* boot_control() = 0;
+
+  // Gets the interface object for the clock.
+  virtual ClockInterface* clock() = 0;
+
+  // Gets the connection manager object.
+  virtual ConnectionManagerInterface* connection_manager() = 0;
+
+  // Gets the hardware interface object.
+  virtual HardwareInterface* hardware() = 0;
+
+  // Gets the Metrics Library interface for reporting UMA stats.
+  virtual MetricsLibraryInterface* metrics_lib() = 0;
+
+  // Gets the interface object for persisted store.
+  virtual PrefsInterface* prefs() = 0;
+
+  // Gets the interface object for the persisted store that persists across
+  // powerwashes. Please note that this should be used very seldomly and must
+  // be forwards and backwards compatible as powerwash is used to go back and
+  // forth in system versions.
+  virtual PrefsInterface* powerwash_safe_prefs() = 0;
+
+  // Gets the interface for the payload state object.
+  virtual PayloadStateInterface* payload_state() = 0;
+
+  // Returns a pointer to the update attempter object.
+  virtual UpdateAttempter* update_attempter() = 0;
+
+  // Returns a pointer to the object that stores the parameters that are
+  // common to all Omaha requests.
+  virtual OmahaRequestParams* request_params() = 0;
+
+  // Returns a pointer to the P2PManager singleton.
+  virtual P2PManager* p2p_manager() = 0;
+
+  // Returns a pointer to the UpdateManager singleton.
+  virtual chromeos_update_manager::UpdateManager* update_manager() = 0;
+
+  // DBus proxies. Mocked during test.
+  virtual org::chromium::PowerManagerProxyInterface* power_manager_proxy() = 0;
+
+  // If true, this is the first instance of the update engine since the system
+  // restarted. Important for tracking whether you are running instance of the
+  // update engine on first boot or due to a crash/restart.
+  virtual bool system_rebooted() = 0;
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_SYSTEM_STATE_H_
diff --git a/tar_bunzip2.gypi b/tar_bunzip2.gypi
new file mode 100644
index 0000000..8c6614a
--- /dev/null
+++ b/tar_bunzip2.gypi
@@ -0,0 +1,42 @@
+#
+# Copyright (C) 2015 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.
+#
+{
+  'variables': {
+    'out_dir': '<(SHARED_INTERMEDIATE_DIR)/<(image_out_dir)',
+  },
+  'rules': [
+    {
+      'rule_name': 'tar-bunzip2',
+      'extension': 'bz2',
+      'inputs': [
+        '<(RULE_INPUT_PATH)',
+      ],
+      'outputs': [
+        # The .flag file is used to mark the timestamp of the file extraction
+        # and re-run this action if a new .bz2 file is generated.
+        '<(out_dir)/<(RULE_INPUT_ROOT).flag',
+      ],
+      'action': [
+        'sh',
+        '-c',
+        'tar -xvf "<(RULE_INPUT_PATH)" -C "<(out_dir)" && touch <(out_dir)/<(RULE_INPUT_ROOT).flag',
+      ],
+      'msvs_cygwin_shell': 0,
+      'process_outputs_as_sources': 1,
+      'message': 'Unpacking file <(RULE_INPUT_PATH)',
+    },
+  ],
+}
diff --git a/test_http_server.cc b/test_http_server.cc
new file mode 100644
index 0000000..eaffba8
--- /dev/null
+++ b/test_http_server.cc
@@ -0,0 +1,634 @@
+//
+// Copyright (C) 2012 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.
+//
+
+// This file implements a simple HTTP server. It can exhibit odd behavior
+// that's useful for testing. For example, it's useful to test that
+// the updater can continue a connection if it's dropped, or that it
+// handles very slow data transfers.
+
+// To use this, simply make an HTTP connection to localhost:port and
+// GET a url.
+
+#include <err.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <inttypes.h>
+#include <netinet/in.h>
+#include <signal.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/socket.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/posix/eintr_wrapper.h>
+#include <base/strings/string_split.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/common/http_common.h"
+
+
+// HTTP end-of-line delimiter; sorry, this needs to be a macro.
+#define EOL "\r\n"
+
+using std::string;
+using std::vector;
+
+
+namespace chromeos_update_engine {
+
+static const char* kListeningMsgPrefix = "listening on port ";
+
+enum {
+  RC_OK = 0,
+  RC_BAD_ARGS,
+  RC_ERR_READ,
+  RC_ERR_SETSOCKOPT,
+  RC_ERR_BIND,
+  RC_ERR_LISTEN,
+  RC_ERR_GETSOCKNAME,
+  RC_ERR_REPORT,
+};
+
+struct HttpRequest {
+  HttpRequest()
+      : start_offset(0), end_offset(0), return_code(kHttpResponseOk) {}
+  string host;
+  string url;
+  off_t start_offset;
+  off_t end_offset;  // non-inclusive, zero indicates unspecified.
+  HttpResponseCode return_code;
+};
+
+bool ParseRequest(int fd, HttpRequest* request) {
+  string headers;
+  do {
+    char buf[1024];
+    ssize_t r = read(fd, buf, sizeof(buf));
+    if (r < 0) {
+      perror("read");
+      exit(RC_ERR_READ);
+    }
+    headers.append(buf, r);
+  } while (!base::EndsWith(headers, EOL EOL, true));
+
+  LOG(INFO) << "got headers:\n--8<------8<------8<------8<----\n"
+            << headers
+            << "\n--8<------8<------8<------8<----";
+
+  // Break header into lines.
+  vector<string> lines;
+  base::SplitStringUsingSubstr(
+      headers.substr(0, headers.length() - strlen(EOL EOL)), EOL, &lines);
+
+  // Decode URL line.
+  vector<string> terms;
+  base::SplitStringAlongWhitespace(lines[0], &terms);
+  CHECK_EQ(terms.size(), static_cast<vector<string>::size_type>(3));
+  CHECK_EQ(terms[0], "GET");
+  request->url = terms[1];
+  LOG(INFO) << "URL: " << request->url;
+
+  // Decode remaining lines.
+  size_t i;
+  for (i = 1; i < lines.size(); i++) {
+    vector<string> terms;
+    base::SplitStringAlongWhitespace(lines[i], &terms);
+
+    if (terms[0] == "Range:") {
+      CHECK_EQ(terms.size(), static_cast<vector<string>::size_type>(2));
+      string &range = terms[1];
+      LOG(INFO) << "range attribute: " << range;
+      CHECK(base::StartsWithASCII(range, "bytes=", true) &&
+            range.find('-') != string::npos);
+      request->start_offset = atoll(range.c_str() + strlen("bytes="));
+      // Decode end offset and increment it by one (so it is non-inclusive).
+      if (range.find('-') < range.length() - 1)
+        request->end_offset = atoll(range.c_str() + range.find('-') + 1) + 1;
+      request->return_code = kHttpResponsePartialContent;
+      string tmp_str = base::StringPrintf("decoded range offsets: "
+                                               "start=%jd end=",
+                                               (intmax_t)request->start_offset);
+      if (request->end_offset > 0)
+        base::StringAppendF(&tmp_str, "%jd (non-inclusive)",
+                            (intmax_t)request->end_offset);
+      else
+        base::StringAppendF(&tmp_str, "unspecified");
+      LOG(INFO) << tmp_str;
+    } else if (terms[0] == "Host:") {
+      CHECK_EQ(terms.size(), static_cast<vector<string>::size_type>(2));
+      request->host = terms[1];
+      LOG(INFO) << "host attribute: " << request->host;
+    } else {
+      LOG(WARNING) << "ignoring HTTP attribute: `" << lines[i] << "'";
+    }
+  }
+
+  return true;
+}
+
+string Itoa(off_t num) {
+  char buf[100] = {0};
+  snprintf(buf, sizeof(buf), "%" PRIi64, num);
+  return buf;
+}
+
+// Writes a string into a file. Returns total number of bytes written or -1 if a
+// write error occurred.
+ssize_t WriteString(int fd, const string& str) {
+  const size_t total_size = str.size();
+  size_t remaining_size = total_size;
+  char const *data = str.data();
+
+  while (remaining_size) {
+    ssize_t written = write(fd, data, remaining_size);
+    if (written < 0) {
+      perror("write");
+      LOG(INFO) << "write failed";
+      return -1;
+    }
+    data += written;
+    remaining_size -= written;
+  }
+
+  return total_size;
+}
+
+// Writes the headers of an HTTP response into a file.
+ssize_t WriteHeaders(int fd, const off_t start_offset, const off_t end_offset,
+                     HttpResponseCode return_code) {
+  ssize_t written = 0, ret;
+
+  ret = WriteString(fd,
+                    string("HTTP/1.1 ") + Itoa(return_code) + " " +
+                    GetHttpResponseDescription(return_code) +
+                    EOL
+                    "Content-Type: application/octet-stream" EOL);
+  if (ret < 0)
+    return -1;
+  written += ret;
+
+  // Compute content legnth.
+  const off_t content_length = end_offset - start_offset;;
+
+  // A start offset that equals the end offset indicates that the response
+  // should contain the full range of bytes in the requested resource.
+  if (start_offset || start_offset == end_offset) {
+    ret = WriteString(fd,
+                      string("Accept-Ranges: bytes" EOL
+                             "Content-Range: bytes ") +
+                      Itoa(start_offset == end_offset ? 0 : start_offset) +
+                      "-" + Itoa(end_offset - 1) + "/" + Itoa(end_offset) +
+                      EOL);
+    if (ret < 0)
+      return -1;
+    written += ret;
+  }
+
+  ret = WriteString(fd, string("Content-Length: ") + Itoa(content_length) +
+                    EOL EOL);
+  if (ret < 0)
+    return -1;
+  written += ret;
+
+  return written;
+}
+
+// Writes a predetermined payload of lines of ascending bytes to a file. The
+// first byte of output is appropriately offset with respect to the request line
+// length.  Returns the number of successfully written bytes.
+size_t WritePayload(int fd, const off_t start_offset, const off_t end_offset,
+                    const char first_byte, const size_t line_len) {
+  CHECK_LE(start_offset, end_offset);
+  CHECK_GT(line_len, static_cast<size_t>(0));
+
+  LOG(INFO) << "writing payload: " << line_len << "-byte lines starting with `"
+            << first_byte << "', offset range " << start_offset << " -> "
+            << end_offset;
+
+  // Populate line of ascending characters.
+  string line;
+  line.reserve(line_len);
+  char byte = first_byte;
+  size_t i;
+  for (i = 0; i < line_len; i++)
+    line += byte++;
+
+  const size_t total_len = end_offset - start_offset;
+  size_t remaining_len = total_len;
+  bool success = true;
+
+  // If start offset is not aligned with line boundary, output partial line up
+  // to the first line boundary.
+  size_t start_modulo = start_offset % line_len;
+  if (start_modulo) {
+    string partial = line.substr(start_modulo, remaining_len);
+    ssize_t ret = WriteString(fd, partial);
+    if ((success = (ret >= 0 && (size_t) ret == partial.length())))
+      remaining_len -= partial.length();
+  }
+
+  // Output full lines up to the maximal line boundary below the end offset.
+  while (success && remaining_len >= line_len) {
+    ssize_t ret = WriteString(fd, line);
+    if ((success = (ret >= 0 && (size_t) ret == line_len)))
+      remaining_len -= line_len;
+  }
+
+  // Output a partial line up to the end offset.
+  if (success && remaining_len) {
+    string partial = line.substr(0, remaining_len);
+    ssize_t ret = WriteString(fd, partial);
+    if ((success = (ret >= 0 && (size_t) ret == partial.length())))
+      remaining_len -= partial.length();
+  }
+
+  return (total_len - remaining_len);
+}
+
+// Write default payload lines of the form 'abcdefghij'.
+inline size_t WritePayload(int fd, const off_t start_offset,
+                           const off_t end_offset) {
+  return WritePayload(fd, start_offset, end_offset, 'a', 10);
+}
+
+// Send an empty response, then kill the server.
+void HandleQuit(int fd) {
+  WriteHeaders(fd, 0, 0, kHttpResponseOk);
+  LOG(INFO) << "pid(" << getpid() <<  "): HTTP server exiting ...";
+  exit(RC_OK);
+}
+
+
+// Generates an HTTP response with payload corresponding to requested offsets
+// and length.  Optionally, truncate the payload at a given length and add a
+// pause midway through the transfer.  Returns the total number of bytes
+// delivered or -1 for error.
+ssize_t HandleGet(int fd, const HttpRequest& request, const size_t total_length,
+                  const size_t truncate_length, const int sleep_every,
+                  const int sleep_secs) {
+  ssize_t ret;
+  size_t written = 0;
+
+  // Obtain start offset, make sure it is within total payload length.
+  const size_t start_offset = request.start_offset;
+  if (start_offset >= total_length) {
+    LOG(WARNING) << "start offset (" << start_offset
+                 << ") exceeds total length (" << total_length
+                 << "), generating error response ("
+                 << kHttpResponseReqRangeNotSat << ")";
+    return WriteHeaders(fd, total_length, total_length,
+                        kHttpResponseReqRangeNotSat);
+  }
+
+  // Obtain end offset, adjust to fit in total payload length and ensure it does
+  // not preceded the start offset.
+  size_t end_offset = (request.end_offset > 0 ?
+                       request.end_offset : total_length);
+  if (end_offset < start_offset) {
+    LOG(WARNING) << "end offset (" << end_offset << ") precedes start offset ("
+                 << start_offset << "), generating error response";
+    return WriteHeaders(fd, 0, 0, kHttpResponseBadRequest);
+  }
+  if (end_offset > total_length) {
+    LOG(INFO) << "requested end offset (" << end_offset
+              << ") exceeds total length (" << total_length << "), adjusting";
+    end_offset = total_length;
+  }
+
+  // Generate headers
+  LOG(INFO) << "generating response header: range=" << start_offset << "-"
+            << (end_offset - 1) << "/" << (end_offset - start_offset)
+            << ", return code=" << request.return_code;
+  if ((ret = WriteHeaders(fd, start_offset, end_offset,
+                          request.return_code)) < 0)
+    return -1;
+  LOG(INFO) << ret << " header bytes written";
+  written += ret;
+
+  // Compute payload length, truncate as necessary.
+  size_t payload_length = end_offset - start_offset;
+  if (truncate_length > 0 && truncate_length < payload_length) {
+    LOG(INFO) << "truncating request payload length (" << payload_length
+              << ") at " << truncate_length;
+    payload_length = truncate_length;
+    end_offset = start_offset + payload_length;
+  }
+
+  LOG(INFO) << "generating response payload: range=" << start_offset << "-"
+            << (end_offset - 1) << "/" << (end_offset - start_offset);
+
+  // Decide about optional midway delay.
+  if (truncate_length > 0 && sleep_every > 0 && sleep_secs >= 0 &&
+      start_offset % (truncate_length * sleep_every) == 0) {
+    const off_t midway_offset = start_offset + payload_length / 2;
+
+    if ((ret = WritePayload(fd, start_offset, midway_offset)) < 0)
+      return -1;
+    LOG(INFO) << ret << " payload bytes written (first chunk)";
+    written += ret;
+
+    LOG(INFO) << "sleeping for " << sleep_secs << " seconds...";
+    sleep(sleep_secs);
+
+    if ((ret = WritePayload(fd, midway_offset, end_offset)) < 0)
+      return -1;
+    LOG(INFO) << ret << " payload bytes written (second chunk)";
+    written += ret;
+  } else {
+    if ((ret = WritePayload(fd, start_offset, end_offset)) < 0)
+      return -1;
+    LOG(INFO) << ret << " payload bytes written";
+    written += ret;
+  }
+
+  LOG(INFO) << "response generation complete, " << written
+            << " total bytes written";
+  return written;
+}
+
+ssize_t HandleGet(int fd, const HttpRequest& request,
+                  const size_t total_length) {
+  return HandleGet(fd, request, total_length, 0, 0, 0);
+}
+
+// Handles /redirect/<code>/<url> requests by returning the specified
+// redirect <code> with a location pointing to /<url>.
+void HandleRedirect(int fd, const HttpRequest& request) {
+  LOG(INFO) << "Redirecting...";
+  string url = request.url;
+  CHECK_EQ(static_cast<size_t>(0), url.find("/redirect/"));
+  url.erase(0, strlen("/redirect/"));
+  string::size_type url_start = url.find('/');
+  CHECK_NE(url_start, string::npos);
+  HttpResponseCode code = StringToHttpResponseCode(url.c_str());
+  url.erase(0, url_start);
+  url = "http://" + request.host + url;
+  const char *status = GetHttpResponseDescription(code);
+  if (!status)
+    CHECK(false) << "Unrecognized redirection code: " << code;
+  LOG(INFO) << "Code: " << code << " " << status;
+  LOG(INFO) << "New URL: " << url;
+
+  ssize_t ret;
+  if ((ret = WriteString(fd, "HTTP/1.1 " + Itoa(code) + " " +
+                         status + EOL)) < 0)
+    return;
+  WriteString(fd, "Location: " + url + EOL);
+}
+
+// Generate a page not found error response with actual text payload. Return
+// number of bytes written or -1 for error.
+ssize_t HandleError(int fd, const HttpRequest& request) {
+  LOG(INFO) << "Generating error HTTP response";
+
+  ssize_t ret;
+  size_t written = 0;
+
+  const string data("This is an error page.");
+
+  if ((ret = WriteHeaders(fd, 0, data.size(), kHttpResponseNotFound)) < 0)
+    return -1;
+  written += ret;
+
+  if ((ret = WriteString(fd, data)) < 0)
+    return -1;
+  written += ret;
+
+  return written;
+}
+
+// Generate an error response if the requested offset is nonzero, up to a given
+// maximal number of successive failures.  The error generated is an "Internal
+// Server Error" (500).
+ssize_t HandleErrorIfOffset(int fd, const HttpRequest& request,
+                            size_t end_offset, int max_fails) {
+  static int num_fails = 0;
+
+  if (request.start_offset > 0 && num_fails < max_fails) {
+    LOG(INFO) << "Generating error HTTP response";
+
+    ssize_t ret;
+    size_t written = 0;
+
+    const string data("This is an error page.");
+
+    if ((ret = WriteHeaders(fd, 0, data.size(),
+                            kHttpResponseInternalServerError)) < 0)
+      return -1;
+    written += ret;
+
+    if ((ret = WriteString(fd, data)) < 0)
+      return -1;
+    written += ret;
+
+    num_fails++;
+    return written;
+  } else {
+    num_fails = 0;
+    return HandleGet(fd, request, end_offset);
+  }
+}
+
+void HandleHang(int fd) {
+  LOG(INFO) << "Hanging until the other side of the connection is closed.";
+  char c;
+  while (HANDLE_EINTR(read(fd, &c, 1)) > 0) {}
+}
+
+void HandleDefault(int fd, const HttpRequest& request) {
+  const off_t start_offset = request.start_offset;
+  const string data("unhandled path");
+  const size_t size = data.size();
+  ssize_t ret;
+
+  if ((ret = WriteHeaders(fd, start_offset, size, request.return_code)) < 0)
+    return;
+  WriteString(fd, (start_offset < static_cast<off_t>(size) ?
+                   data.substr(start_offset) : ""));
+}
+
+
+// Break a URL into terms delimited by slashes.
+class UrlTerms {
+ public:
+  UrlTerms(const string &url, size_t num_terms) {
+    // URL must be non-empty and start with a slash.
+    CHECK_GT(url.size(), static_cast<size_t>(0));
+    CHECK_EQ(url[0], '/');
+
+    // Split it into terms delimited by slashes, omitting the preceeding slash.
+    base::SplitStringDontTrim(url.substr(1), '/', &terms);
+
+    // Ensure expected length.
+    CHECK_EQ(terms.size(), num_terms);
+  }
+
+  inline string Get(const off_t index) const {
+    return terms[index];
+  }
+  inline const char *GetCStr(const off_t index) const {
+    return Get(index).c_str();
+  }
+  inline int GetInt(const off_t index) const {
+    return atoi(GetCStr(index));
+  }
+  inline size_t GetSizeT(const off_t index) const {
+    return static_cast<size_t>(atol(GetCStr(index)));
+  }
+
+ private:
+  vector<string> terms;
+};
+
+void HandleConnection(int fd) {
+  HttpRequest request;
+  ParseRequest(fd, &request);
+
+  string &url = request.url;
+  LOG(INFO) << "pid(" << getpid() <<  "): handling url " << url;
+  if (url == "/quitquitquit") {
+    HandleQuit(fd);
+  } else if (base::StartsWithASCII(url, "/download/", true)) {
+    const UrlTerms terms(url, 2);
+    HandleGet(fd, request, terms.GetSizeT(1));
+  } else if (base::StartsWithASCII(url, "/flaky/", true)) {
+    const UrlTerms terms(url, 5);
+    HandleGet(fd, request, terms.GetSizeT(1), terms.GetSizeT(2),
+              terms.GetInt(3), terms.GetInt(4));
+  } else if (url.find("/redirect/") == 0) {
+    HandleRedirect(fd, request);
+  } else if (url == "/error") {
+    HandleError(fd, request);
+  } else if (base::StartsWithASCII(url, "/error-if-offset/", true)) {
+    const UrlTerms terms(url, 3);
+    HandleErrorIfOffset(fd, request, terms.GetSizeT(1), terms.GetInt(2));
+  } else if (url == "/hang") {
+    HandleHang(fd);
+  } else {
+    HandleDefault(fd, request);
+  }
+
+  close(fd);
+}
+
+}  // namespace chromeos_update_engine
+
+using namespace chromeos_update_engine;  // NOLINT(build/namespaces)
+
+
+void usage(const char *prog_arg) {
+  fprintf(
+      stderr,
+      "Usage: %s [ FILE ]\n"
+      "Once accepting connections, the following is written to FILE (or "
+      "stdout):\n"
+      "\"%sN\" (where N is an integer port number)\n",
+      basename(prog_arg), kListeningMsgPrefix);
+}
+
+int main(int argc, char** argv) {
+  // Check invocation.
+  if (argc > 2)
+    errx(RC_BAD_ARGS, "unexpected number of arguments (use -h for usage)");
+
+  // Parse (optional) argument.
+  int report_fd = STDOUT_FILENO;
+  if (argc == 2) {
+    if (!strcmp(argv[1], "-h")) {
+      usage(argv[0]);
+      exit(RC_OK);
+    }
+
+    report_fd = open(argv[1], O_WRONLY | O_CREAT, 00644);
+  }
+
+  // Ignore SIGPIPE on write() to sockets.
+  signal(SIGPIPE, SIG_IGN);
+
+  int listen_fd = socket(AF_INET, SOCK_STREAM, 0);
+  if (listen_fd < 0)
+    LOG(FATAL) << "socket() failed";
+
+  struct sockaddr_in server_addr = sockaddr_in();
+  server_addr.sin_family = AF_INET;
+  server_addr.sin_addr.s_addr = INADDR_ANY;
+  server_addr.sin_port = 0;
+
+  {
+    // Get rid of "Address in use" error
+    int tr = 1;
+    if (setsockopt(listen_fd, SOL_SOCKET, SO_REUSEADDR, &tr,
+                   sizeof(int)) == -1) {
+      perror("setsockopt");
+      exit(RC_ERR_SETSOCKOPT);
+    }
+  }
+
+  // Bind the socket and set for listening.
+  if (bind(listen_fd, reinterpret_cast<struct sockaddr *>(&server_addr),
+           sizeof(server_addr)) < 0) {
+    perror("bind");
+    exit(RC_ERR_BIND);
+  }
+  if (listen(listen_fd, 5) < 0) {
+    perror("listen");
+    exit(RC_ERR_LISTEN);
+  }
+
+  // Check the actual port.
+  struct sockaddr_in bound_addr = sockaddr_in();
+  socklen_t bound_addr_len = sizeof(bound_addr);
+  if (getsockname(listen_fd, reinterpret_cast<struct sockaddr*>(&bound_addr),
+                  &bound_addr_len) < 0) {
+    perror("getsockname");
+    exit(RC_ERR_GETSOCKNAME);
+  }
+  in_port_t port = ntohs(bound_addr.sin_port);
+
+  // Output the listening port, indicating that the server is processing
+  // requests. IMPORTANT! (a) the format of this message is as expected by some
+  // unit tests, avoid unilateral changes; (b) it is necessary to flush/sync the
+  // file to prevent the spawning process from waiting indefinitely for this
+  // message.
+  string listening_msg = base::StringPrintf("%s%hu", kListeningMsgPrefix, port);
+  LOG(INFO) << listening_msg;
+  CHECK_EQ(write(report_fd, listening_msg.c_str(), listening_msg.length()),
+           static_cast<int>(listening_msg.length()));
+  CHECK_EQ(write(report_fd, "\n", 1), 1);
+  if (report_fd == STDOUT_FILENO)
+    fsync(report_fd);
+  else
+    close(report_fd);
+
+  while (1) {
+    LOG(INFO) << "pid(" << getpid() <<  "): waiting to accept new connection";
+    int client_fd = accept(listen_fd, nullptr, nullptr);
+    LOG(INFO) << "got past accept";
+    if (client_fd < 0)
+      LOG(FATAL) << "ERROR on accept";
+    HandleConnection(client_fd);
+  }
+  return 0;
+}
diff --git a/testrunner.cc b/testrunner.cc
new file mode 100644
index 0000000..9e22798
--- /dev/null
+++ b/testrunner.cc
@@ -0,0 +1,47 @@
+//
+// Copyright (C) 2012 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.
+//
+
+// based on pam_google_testrunner.cc
+
+#include <xz.h>
+
+#include <base/at_exit.h>
+#include <base/command_line.h>
+#include <brillo/test_helpers.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/terminator.h"
+
+int main(int argc, char **argv) {
+  LOG(INFO) << "started";
+  base::AtExitManager exit_manager;
+  // xz-embedded requires to initialize its CRC-32 table once on startup.
+  xz_crc32_init();
+  // TODO(garnold) temporarily cause the unittest binary to exit with status
+  // code 2 upon catching a SIGTERM. This will help diagnose why the unittest
+  // binary is perceived as failing by the buildbot.  We should revert it to use
+  // the default exit status of 1.  Corresponding reverts are necessary in
+  // terminator_unittest.cc.
+  chromeos_update_engine::Terminator::Init(2);
+  LOG(INFO) << "parsing command line arguments";
+  base::CommandLine::Init(argc, argv);
+  LOG(INFO) << "initializing gtest";
+  SetUpTests(&argc, argv, true);
+  LOG(INFO) << "running unit tests";
+  int test_result = RUN_ALL_TESTS();
+  LOG(INFO) << "unittest return value: " << test_result;
+  return test_result;
+}
diff --git a/unittest_key.pem b/unittest_key.pem
new file mode 100644
index 0000000..224d3c3
--- /dev/null
+++ b/unittest_key.pem
@@ -0,0 +1,27 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIEpAIBAAKCAQEAx6hqS+Hbc7jN82ek+OBkHJNvlWXktyS2XCuQtGtnHjEV7Ou5
+hHNF96s5wEn8RDtrdLocm0a+SqXXf7KycFRTZxLdDbqWAMUlPXOaPI+PZLWkB7/K
+V7Cdj6vPGbeq7elu+aT/budhzTvq2stYrrAlcr/21tOVDPiWtfCdykh7FCXi6FaY
+HoNy5A6EKQLfLBuJoU/QoCufldmwlFaFDKl+Koos6R1QYJfCNZfgocrW1PIh+8t1
+JIvw6Izo8+fTme7nev7Ol2YZiMWJpRYKx8MgxW2UgTXlRpmQN56pc9LUsnVA8FND
+BN57+gMJj+XmdDmbtMpOsyXfSNEgnuwMPcEcmwIDAQABAoIBABPkwgKhlH4pUcwI
+7bUmlpMKVbnrFyjwbYMtjBOOCA5IEckzi56Y5cXRt8VjGdGqogBVcvg9ykQh1iER
+KxpqLI0+oev2RW/6NMW0uQ+DtmPwfVGQWJb4MBraoZ4MYOmnsrkJKbJhN6t9Zt86
+F7IANxsB6ZRqLJXIRywFt5MqOak+GAnQJ8C8eSQg70NhbEhSOrD8wrD6tfvgIqta
+XxhtlQWUAILIWetnWrJsalMqnreGn7vhc7+iihhMtXh1xNBMTA+gzpov/Cx21iH5
+DM9ppSA6HHDXrMhauryypIRrhjOUWRyDws/kIHgIW4TCbULOlxqsputQeTmdf0ti
+7lpwqAECgYEA7nNKkct3Vs51Ugk4GUPC4NOyYRPNc9UQAfHViB9gSDRacCo9Ax9J
+83hJGqDXlNGzELOnhzMn8jQMyF13eWzOsMozK6Fj3uW7DBvelg5bfgsZDUUO5WUF
+6BYbOheVqf12rIHR9BKBmCfLEKyxbKmw5bnB0uNo7IuBPBNuhPbvkgECgYEA1lo5
+XHWJpQnVl+JzXLHpXBK2nfnFAOtvzlTW+7gteeU12X2HcFASrzp7C1ULVV+i1Kcz
+tDFIA5yiFjEqmSJ/TsO8aqAhL5BXJjylCepQK7XkEOGCR8eQjlt7E4DulAsQbfpt
+k30HVVlIOFqLCWKSW8M3dy/Plodq/Gyq26rntpsCgYAzsNyGdIQfVkxKh2MY3v6c
+/Gdb8g4EwThiI4m1o4+ct3SvggiN57eBRx8Z3ao+QaM+yKNVhLpxH+VxfgmLUhIQ
+cxTarXbX+BcvTc9X2i7tSPyaStEq21aHdFtcoYY5Po/+X3ojHevoDyBPMhCYTMTj
+V/xzegbh2HAglNnNizZuAQKBgQCyOxEpBP5vgS7d/MgJklFEYrb/wjgBnMI5oSek
+5C7EBUdyUUM1qw7uLsUy1gL3eO7uvRxrvvJvNmU76KPP8vRCLNTVH9KYNv+P5qsg
+BHmm7rX1J11pi9Fx3TUIMZOu+0gs+ib0lOhtGjDH0tl680BZFohfDR0hv/XAcCbd
+Qk0q8wKBgQCGbURFFW/5RZUA77MmpY6jsEMw2gJmVtjO5IWZg9VPvLQQPgCr4Ho/
+bS2LIsT6pS+hrLOoz5KI0YueRS0jQYI+WkRqNf5wYNjxPql9632FiDLHO+Xv8PBe
+kHrPHy0GGT1igXScY4eemw4ZC1OSdZfkVn6Ui/JvBHrydJ2LrutMWQ==
+-----END RSA PRIVATE KEY-----
diff --git a/unittest_key2.pem b/unittest_key2.pem
new file mode 100644
index 0000000..d1f9a78
--- /dev/null
+++ b/unittest_key2.pem
@@ -0,0 +1,27 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIEpAIBAAKCAQEAqdM7gnd43cWfQzyrt16QDHE+T0yxg18OZO+9sc8jWpjC1zFt
+oMFokESiu9TLUp+KUC274f+DxIgAfSCO6U5DJFRPXUzve1vaXYfqljUBxc+JYcGd
+d6PCUl4Ap9f02DhkrGnf/rkHOCEhFNpm53dovZ9A6Q5KBfcg1HeQ088opVceQGtU
+mL+bONq5tLvNFLUU0Ru0Am4ADJ8Xmw4rpvqvmXJaFmVuf/Gx7+TOnaJvZTeOO9AJ
+K6q6V8E7+ZZiMIc5F4EOs5AX/lZfNO3RVgG2O7Dhzza+nOzJ3ZJGK5R4WwZduhn9
+QRYogYPB0c62878qXpf2Bn3NpUPi8Cf/RLMMmQIDAQABAoIBACyLUWKpP7S770hN
+k6TnUtVQps1aCn2w4y+qipEnCdjrlL+pIV43HNwqhJzL9gDYBAl/1XYz9TYJjkdD
+0Ph1JLtUufR5B5/NufsqeWeow6xFAX34sPr+oyvDqFxeEsTcFdv7cVt44OHiHrE/
+kBpKgdiq+vWmX9gsuBnCuuQzxC+Juo6nupwZXcpa/ow9lC4QsgKqcjaUGrXXy2t9
+Er+9aSl8NdTjK76BXQsDgNkDyJZwNN14xrdS8eFsS4twskaOEYI4hEM0g62NOjgd
+Po8Ap/MnPpGSGcAd3d3Fq8KgT1lpyMKedLFU+k0H+/Y4RBl7grz1XXvSTzGi3Qy6
+38F4eVkCgYEA4mo4iiXSfrov9QffsVM17O0t9hUsOJHnUsEScxWLDm4IzaObyTtv
+tWW33iQSeFu4Wsol0nzjqWo3BaqiRidRUd42yZ07LJvfUDxUX9xPaUPFRs25iwhZ
+6tKAVqGk7/CFrN+R44sIwbsSvbExMAyW6gnj93EWUmMWWYp02hLbN0sCgYEAwAQI
+awVoc56OCtRpfYtlAPD/VOP1mbNzRmVl/UyZ4XYmz6f/hEz63Bk5PhYSZftlmK/r
+nj4qnl7HZ8jrJgZn2e97rPNpk7KDVU1+csCgLWZBTOXl/o9tOTyjh9LoRAjKtBB7
+x6CkWyiyd94xIq5VbnXhvL3a4d4o6OxMWdG5aSsCgYEAo44z1afIzP7WkdzkPIZt
+l/8linR1A1BymBccqsHPN9dIyLP9X3puEc2u6uuH5CXtoLgSZmENXF577L38h0zz
+s34gebf4/RqEUMOj97OAMfxgz+rgs4yO19DEINCYAzPufJjsHEFdTAVFXn5Xl+wg
+QGRwp1ir1Uv64yffjYC9ls0CgYEAjvIxpiKniPNvwUYypmDgt5uyKetvCpaaabzQ
++YpOQJep+wuRYFfCpZotkDf0SHGoR8wnd23GYpIilvPvgyZfp9HuW2n2nhrWROnl
+Cd63IDUwxeOcni7+XA71mwb7HLMC3Jws2geQc8DPZAdIww3P0eT2QYGBcobmI8jO
+akuEYXMCgYAm79Kb/r+3Hew5oAS1Whw70DskVlOutSgNsDPfW9MtDcnETBcGep7A
+1jCL5jjdUYRonimVMFjh1K+UFzV/DQHkgNzjxz9Inbh02y67vL2X836dS9esOcbx
+uZhf+8rL+GnSNqYDqCEuP7qCIloDhguJq9NKyTB4yc59qIkY2zPAzQ==
+-----END RSA PRIVATE KEY-----
diff --git a/update_attempter.cc b/update_attempter.cc
new file mode 100644
index 0000000..5704731
--- /dev/null
+++ b/update_attempter.cc
@@ -0,0 +1,1604 @@
+//
+// Copyright (C) 2012 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 "update_engine/update_attempter.h"
+
+#include <stdint.h>
+
+#include <algorithm>
+#include <memory>
+#include <set>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/files/file_util.h>
+#include <base/logging.h>
+#include <base/rand_util.h>
+#include <base/strings/string_util.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/message_loop.h>
+#include <debugd/dbus-constants.h>
+#include <policy/device_policy.h>
+#include <policy/libpolicy.h>
+#include <power_manager/dbus-constants.h>
+#include <power_manager/dbus-proxies.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/constants.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/common/libcurl_http_fetcher.h"
+#include "update_engine/common/multi_range_http_fetcher.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs_interface.h"
+#include "update_engine/common/subprocess.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/dbus_service.h"
+#include "update_engine/metrics.h"
+#include "update_engine/omaha_request_action.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/omaha_response_handler_action.h"
+#include "update_engine/p2p_manager.h"
+#include "update_engine/payload_consumer/download_action.h"
+#include "update_engine/payload_consumer/filesystem_verifier_action.h"
+#include "update_engine/payload_consumer/postinstall_runner_action.h"
+#include "update_engine/payload_state_interface.h"
+#include "update_engine/system_state.h"
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/update_manager.h"
+#include "update_engine/update_status_utils.h"
+
+using base::Bind;
+using base::Callback;
+using base::Time;
+using base::TimeDelta;
+using base::TimeTicks;
+using brillo::MessageLoop;
+using chromeos_update_manager::EvalStatus;
+using chromeos_update_manager::Policy;
+using chromeos_update_manager::UpdateCheckParams;
+using std::set;
+using std::shared_ptr;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_engine {
+
+const int UpdateAttempter::kMaxDeltaUpdateFailures = 3;
+
+namespace {
+const int kMaxConsecutiveObeyProxyRequests = 20;
+
+// By default autest bypasses scattering. If we want to test scattering,
+// use kScheduledAUTestURLRequest. The URL used is same in both cases, but
+// different params are passed to CheckForUpdate().
+const char kAUTestURLRequest[] = "autest";
+const char kScheduledAUTestURLRequest[] = "autest-scheduled";
+}  // namespace
+
+// Turns a generic ErrorCode::kError to a generic error code specific
+// to |action| (e.g., ErrorCode::kFilesystemVerifierError). If |code| is
+// not ErrorCode::kError, or the action is not matched, returns |code|
+// unchanged.
+ErrorCode GetErrorCodeForAction(AbstractAction* action,
+                                     ErrorCode code) {
+  if (code != ErrorCode::kError)
+    return code;
+
+  const string type = action->Type();
+  if (type == OmahaRequestAction::StaticType())
+    return ErrorCode::kOmahaRequestError;
+  if (type == OmahaResponseHandlerAction::StaticType())
+    return ErrorCode::kOmahaResponseHandlerError;
+  if (type == FilesystemVerifierAction::StaticType())
+    return ErrorCode::kFilesystemVerifierError;
+  if (type == PostinstallRunnerAction::StaticType())
+    return ErrorCode::kPostinstallRunnerError;
+
+  return code;
+}
+
+UpdateAttempter::UpdateAttempter(
+    SystemState* system_state,
+    CertificateChecker* cert_checker,
+    LibCrosProxy* libcros_proxy,
+    org::chromium::debugdProxyInterface* debugd_proxy)
+    : processor_(new ActionProcessor()),
+      system_state_(system_state),
+      cert_checker_(cert_checker),
+      chrome_proxy_resolver_(libcros_proxy),
+      debugd_proxy_(debugd_proxy) {
+}
+
+UpdateAttempter::~UpdateAttempter() {
+  // CertificateChecker might not be initialized in unittests.
+  if (cert_checker_)
+    cert_checker_->SetObserver(nullptr);
+  CleanupCpuSharesManagement();
+  // Release ourselves as the ActionProcessor's delegate to prevent
+  // re-scheduling the updates due to the processing stopped.
+  processor_->set_delegate(nullptr);
+}
+
+void UpdateAttempter::Init() {
+  // Pulling from the SystemState can only be done after construction, since
+  // this is an aggregate of various objects (such as the UpdateAttempter),
+  // which requires them all to be constructed prior to it being used.
+  prefs_ = system_state_->prefs();
+  omaha_request_params_ = system_state_->request_params();
+
+  if (cert_checker_)
+    cert_checker_->SetObserver(this);
+
+  // In case of update_engine restart without a reboot we need to restore the
+  // reboot needed state.
+  if (GetBootTimeAtUpdate(nullptr))
+    status_ = UpdateStatus::UPDATED_NEED_REBOOT;
+  else
+    status_ = UpdateStatus::IDLE;
+
+  chrome_proxy_resolver_.Init();
+}
+
+void UpdateAttempter::ScheduleUpdates() {
+  if (IsUpdateRunningOrScheduled())
+    return;
+
+  chromeos_update_manager::UpdateManager* const update_manager =
+      system_state_->update_manager();
+  CHECK(update_manager);
+  Callback<void(EvalStatus, const UpdateCheckParams&)> callback = Bind(
+      &UpdateAttempter::OnUpdateScheduled, base::Unretained(this));
+  // We limit the async policy request to a reasonably short time, to avoid a
+  // starvation due to a transient bug.
+  update_manager->AsyncPolicyRequest(callback, &Policy::UpdateCheckAllowed);
+  waiting_for_scheduled_check_ = true;
+}
+
+void UpdateAttempter::CertificateChecked(ServerToCheck server_to_check,
+                                         CertificateCheckResult result) {
+  metrics::ReportCertificateCheckMetrics(system_state_,
+                                         server_to_check,
+                                         result);
+}
+
+bool UpdateAttempter::CheckAndReportDailyMetrics() {
+  int64_t stored_value;
+  Time now = system_state_->clock()->GetWallclockTime();
+  if (system_state_->prefs()->Exists(kPrefsDailyMetricsLastReportedAt) &&
+      system_state_->prefs()->GetInt64(kPrefsDailyMetricsLastReportedAt,
+                                       &stored_value)) {
+    Time last_reported_at = Time::FromInternalValue(stored_value);
+    TimeDelta time_reported_since = now - last_reported_at;
+    if (time_reported_since.InSeconds() < 0) {
+      LOG(WARNING) << "Last reported daily metrics "
+                   << utils::FormatTimeDelta(time_reported_since) << " ago "
+                   << "which is negative. Either the system clock is wrong or "
+                   << "the kPrefsDailyMetricsLastReportedAt state variable "
+                   << "is wrong.";
+      // In this case, report daily metrics to reset.
+    } else {
+      if (time_reported_since.InSeconds() < 24*60*60) {
+        LOG(INFO) << "Last reported daily metrics "
+                  << utils::FormatTimeDelta(time_reported_since) << " ago.";
+        return false;
+      }
+      LOG(INFO) << "Last reported daily metrics "
+                << utils::FormatTimeDelta(time_reported_since) << " ago, "
+                << "which is more than 24 hours ago.";
+    }
+  }
+
+  LOG(INFO) << "Reporting daily metrics.";
+  system_state_->prefs()->SetInt64(kPrefsDailyMetricsLastReportedAt,
+                                   now.ToInternalValue());
+
+  ReportOSAge();
+
+  return true;
+}
+
+void UpdateAttempter::ReportOSAge() {
+  struct stat sb;
+
+  if (system_state_ == nullptr)
+    return;
+
+  if (stat("/etc/lsb-release", &sb) != 0) {
+    PLOG(ERROR) << "Error getting file status for /etc/lsb-release "
+                << "(Note: this may happen in some unit tests)";
+    return;
+  }
+
+  Time lsb_release_timestamp = utils::TimeFromStructTimespec(&sb.st_ctim);
+  Time now = system_state_->clock()->GetWallclockTime();
+  TimeDelta age = now - lsb_release_timestamp;
+  if (age.InSeconds() < 0) {
+    LOG(ERROR) << "The OS age (" << utils::FormatTimeDelta(age)
+               << ") is negative. Maybe the clock is wrong? "
+               << "(Note: this may happen in some unit tests.)";
+    return;
+  }
+
+  metrics::ReportDailyMetrics(system_state_, age);
+}
+
+void UpdateAttempter::Update(const string& app_version,
+                             const string& omaha_url,
+                             const string& target_channel,
+                             const string& target_version_prefix,
+                             bool obey_proxies,
+                             bool interactive) {
+  // This is normally called frequently enough so it's appropriate to use as a
+  // hook for reporting daily metrics.
+  // TODO(garnold) This should be hooked to a separate (reliable and consistent)
+  // timeout event.
+  CheckAndReportDailyMetrics();
+
+  // Notify of the new update attempt, clearing prior interactive requests.
+  if (forced_update_pending_callback_.get())
+    forced_update_pending_callback_->Run(false, false);
+
+  fake_update_success_ = false;
+  if (status_ == UpdateStatus::UPDATED_NEED_REBOOT) {
+    // Although we have applied an update, we still want to ping Omaha
+    // to ensure the number of active statistics is accurate.
+    //
+    // Also convey to the UpdateEngine.Check.Result metric that we're
+    // not performing an update check because of this.
+    LOG(INFO) << "Not updating b/c we already updated and we're waiting for "
+              << "reboot, we'll ping Omaha instead";
+    metrics::ReportUpdateCheckMetrics(system_state_,
+                                      metrics::CheckResult::kRebootPending,
+                                      metrics::CheckReaction::kUnset,
+                                      metrics::DownloadErrorCode::kUnset);
+    PingOmaha();
+    return;
+  }
+  if (status_ != UpdateStatus::IDLE) {
+    // Update in progress. Do nothing
+    return;
+  }
+
+  if (!CalculateUpdateParams(app_version,
+                             omaha_url,
+                             target_channel,
+                             target_version_prefix,
+                             obey_proxies,
+                             interactive)) {
+    return;
+  }
+
+  BuildUpdateActions(interactive);
+
+  SetStatusAndNotify(UpdateStatus::CHECKING_FOR_UPDATE);
+
+  // Update the last check time here; it may be re-updated when an Omaha
+  // response is received, but this will prevent us from repeatedly scheduling
+  // checks in the case where a response is not received.
+  UpdateLastCheckedTime();
+
+  // Just in case we didn't update boot flags yet, make sure they're updated
+  // before any update processing starts.
+  start_action_processor_ = true;
+  UpdateBootFlags();
+}
+
+void UpdateAttempter::RefreshDevicePolicy() {
+  // Lazy initialize the policy provider, or reload the latest policy data.
+  if (!policy_provider_.get())
+    policy_provider_.reset(new policy::PolicyProvider());
+  policy_provider_->Reload();
+
+  const policy::DevicePolicy* device_policy = nullptr;
+  if (policy_provider_->device_policy_is_loaded())
+    device_policy = &policy_provider_->GetDevicePolicy();
+
+  if (device_policy)
+    LOG(INFO) << "Device policies/settings present";
+  else
+    LOG(INFO) << "No device policies/settings present.";
+
+  system_state_->set_device_policy(device_policy);
+  system_state_->p2p_manager()->SetDevicePolicy(device_policy);
+}
+
+void UpdateAttempter::CalculateP2PParams(bool interactive) {
+  bool use_p2p_for_downloading = false;
+  bool use_p2p_for_sharing = false;
+
+  // Never use p2p for downloading in interactive checks unless the
+  // developer has opted in for it via a marker file.
+  //
+  // (Why would a developer want to opt in? If he's working on the
+  // update_engine or p2p codebases so he can actually test his
+  // code.).
+
+  if (system_state_ != nullptr) {
+    if (!system_state_->p2p_manager()->IsP2PEnabled()) {
+      LOG(INFO) << "p2p is not enabled - disallowing p2p for both"
+                << " downloading and sharing.";
+    } else {
+      // Allow p2p for sharing, even in interactive checks.
+      use_p2p_for_sharing = true;
+      if (!interactive) {
+        LOG(INFO) << "Non-interactive check - allowing p2p for downloading";
+        use_p2p_for_downloading = true;
+      } else {
+        LOG(INFO) << "Forcibly disabling use of p2p for downloading "
+                  << "since this update attempt is interactive.";
+      }
+    }
+  }
+
+  PayloadStateInterface* const payload_state = system_state_->payload_state();
+  payload_state->SetUsingP2PForDownloading(use_p2p_for_downloading);
+  payload_state->SetUsingP2PForSharing(use_p2p_for_sharing);
+}
+
+bool UpdateAttempter::CalculateUpdateParams(const string& app_version,
+                                            const string& omaha_url,
+                                            const string& target_channel,
+                                            const string& target_version_prefix,
+                                            bool obey_proxies,
+                                            bool interactive) {
+  http_response_code_ = 0;
+  PayloadStateInterface* const payload_state = system_state_->payload_state();
+
+  // Refresh the policy before computing all the update parameters.
+  RefreshDevicePolicy();
+
+  // Set the target version prefix, if provided.
+  if (!target_version_prefix.empty())
+    omaha_request_params_->set_target_version_prefix(target_version_prefix);
+
+  CalculateScatteringParams(interactive);
+
+  CalculateP2PParams(interactive);
+  if (payload_state->GetUsingP2PForDownloading() ||
+      payload_state->GetUsingP2PForSharing()) {
+    // OK, p2p is to be used - start it and perform housekeeping.
+    if (!StartP2PAndPerformHousekeeping()) {
+      // If this fails, disable p2p for this attempt
+      LOG(INFO) << "Forcibly disabling use of p2p since starting p2p or "
+                << "performing housekeeping failed.";
+      payload_state->SetUsingP2PForDownloading(false);
+      payload_state->SetUsingP2PForSharing(false);
+    }
+  }
+
+  if (!omaha_request_params_->Init(app_version,
+                                   omaha_url,
+                                   interactive)) {
+    LOG(ERROR) << "Unable to initialize Omaha request params.";
+    return false;
+  }
+
+  // Set the target channel, if one was provided.
+  if (target_channel.empty()) {
+    LOG(INFO) << "No target channel mandated by policy.";
+  } else {
+    LOG(INFO) << "Setting target channel as mandated: " << target_channel;
+    // Pass in false for powerwash_allowed until we add it to the policy
+    // protobuf.
+    string error_message;
+    if (!omaha_request_params_->SetTargetChannel(target_channel, false,
+                                                 &error_message)) {
+      LOG(ERROR) << "Setting the channel failed: " << error_message;
+    }
+
+    // Since this is the beginning of a new attempt, update the download
+    // channel. The download channel won't be updated until the next attempt,
+    // even if target channel changes meanwhile, so that how we'll know if we
+    // should cancel the current download attempt if there's such a change in
+    // target channel.
+    omaha_request_params_->UpdateDownloadChannel();
+  }
+
+  LOG(INFO) << "target_version_prefix = "
+            << omaha_request_params_->target_version_prefix()
+            << ", scatter_factor_in_seconds = "
+            << utils::FormatSecs(scatter_factor_.InSeconds());
+
+  LOG(INFO) << "Wall Clock Based Wait Enabled = "
+            << omaha_request_params_->wall_clock_based_wait_enabled()
+            << ", Update Check Count Wait Enabled = "
+            << omaha_request_params_->update_check_count_wait_enabled()
+            << ", Waiting Period = " << utils::FormatSecs(
+               omaha_request_params_->waiting_period().InSeconds());
+
+  LOG(INFO) << "Use p2p For Downloading = "
+            << payload_state->GetUsingP2PForDownloading()
+            << ", Use p2p For Sharing = "
+            << payload_state->GetUsingP2PForSharing();
+
+  obeying_proxies_ = true;
+  if (obey_proxies || proxy_manual_checks_ == 0) {
+    LOG(INFO) << "forced to obey proxies";
+    // If forced to obey proxies, every 20th request will not use proxies
+    proxy_manual_checks_++;
+    LOG(INFO) << "proxy manual checks: " << proxy_manual_checks_;
+    if (proxy_manual_checks_ >= kMaxConsecutiveObeyProxyRequests) {
+      proxy_manual_checks_ = 0;
+      obeying_proxies_ = false;
+    }
+  } else if (base::RandInt(0, 4) == 0) {
+    obeying_proxies_ = false;
+  }
+  LOG_IF(INFO, !obeying_proxies_) << "To help ensure updates work, this update "
+      "check we are ignoring the proxy settings and using "
+      "direct connections.";
+
+  DisableDeltaUpdateIfNeeded();
+  return true;
+}
+
+void UpdateAttempter::CalculateScatteringParams(bool interactive) {
+  // Take a copy of the old scatter value before we update it, as
+  // we need to update the waiting period if this value changes.
+  TimeDelta old_scatter_factor = scatter_factor_;
+  const policy::DevicePolicy* device_policy = system_state_->device_policy();
+  if (device_policy) {
+    int64_t new_scatter_factor_in_secs = 0;
+    device_policy->GetScatterFactorInSeconds(&new_scatter_factor_in_secs);
+    if (new_scatter_factor_in_secs < 0)  // sanitize input, just in case.
+      new_scatter_factor_in_secs  = 0;
+    scatter_factor_ = TimeDelta::FromSeconds(new_scatter_factor_in_secs);
+  }
+
+  bool is_scatter_enabled = false;
+  if (scatter_factor_.InSeconds() == 0) {
+    LOG(INFO) << "Scattering disabled since scatter factor is set to 0";
+  } else if (interactive) {
+    LOG(INFO) << "Scattering disabled as this is an interactive update check";
+  } else if (!system_state_->hardware()->IsOOBEComplete(nullptr)) {
+    LOG(INFO) << "Scattering disabled since OOBE is not complete yet";
+  } else {
+    is_scatter_enabled = true;
+    LOG(INFO) << "Scattering is enabled";
+  }
+
+  if (is_scatter_enabled) {
+    // This means the scattering policy is turned on.
+    // Now check if we need to update the waiting period. The two cases
+    // in which we'd need to update the waiting period are:
+    // 1. First time in process or a scheduled check after a user-initiated one.
+    //    (omaha_request_params_->waiting_period will be zero in this case).
+    // 2. Admin has changed the scattering policy value.
+    //    (new scattering value will be different from old one in this case).
+    int64_t wait_period_in_secs = 0;
+    if (omaha_request_params_->waiting_period().InSeconds() == 0) {
+      // First case. Check if we have a suitable value to set for
+      // the waiting period.
+      if (prefs_->GetInt64(kPrefsWallClockWaitPeriod, &wait_period_in_secs) &&
+          wait_period_in_secs > 0 &&
+          wait_period_in_secs <= scatter_factor_.InSeconds()) {
+        // This means:
+        // 1. There's a persisted value for the waiting period available.
+        // 2. And that persisted value is still valid.
+        // So, in this case, we should reuse the persisted value instead of
+        // generating a new random value to improve the chances of a good
+        // distribution for scattering.
+        omaha_request_params_->set_waiting_period(
+          TimeDelta::FromSeconds(wait_period_in_secs));
+        LOG(INFO) << "Using persisted wall-clock waiting period: " <<
+            utils::FormatSecs(
+                omaha_request_params_->waiting_period().InSeconds());
+      } else {
+        // This means there's no persisted value for the waiting period
+        // available or its value is invalid given the new scatter_factor value.
+        // So, we should go ahead and regenerate a new value for the
+        // waiting period.
+        LOG(INFO) << "Persisted value not present or not valid ("
+                  << utils::FormatSecs(wait_period_in_secs)
+                  << ") for wall-clock waiting period.";
+        GenerateNewWaitingPeriod();
+      }
+    } else if (scatter_factor_ != old_scatter_factor) {
+      // This means there's already a waiting period value, but we detected
+      // a change in the scattering policy value. So, we should regenerate the
+      // waiting period to make sure it's within the bounds of the new scatter
+      // factor value.
+      GenerateNewWaitingPeriod();
+    } else {
+      // Neither the first time scattering is enabled nor the scattering value
+      // changed. Nothing to do.
+      LOG(INFO) << "Keeping current wall-clock waiting period: " <<
+          utils::FormatSecs(
+              omaha_request_params_->waiting_period().InSeconds());
+    }
+
+    // The invariant at this point is that omaha_request_params_->waiting_period
+    // is non-zero no matter which path we took above.
+    LOG_IF(ERROR, omaha_request_params_->waiting_period().InSeconds() == 0)
+        << "Waiting Period should NOT be zero at this point!!!";
+
+    // Since scattering is enabled, wall clock based wait will always be
+    // enabled.
+    omaha_request_params_->set_wall_clock_based_wait_enabled(true);
+
+    // If we don't have any issues in accessing the file system to update
+    // the update check count value, we'll turn that on as well.
+    bool decrement_succeeded = DecrementUpdateCheckCount();
+    omaha_request_params_->set_update_check_count_wait_enabled(
+      decrement_succeeded);
+  } else {
+    // This means the scattering feature is turned off or disabled for
+    // this particular update check. Make sure to disable
+    // all the knobs and artifacts so that we don't invoke any scattering
+    // related code.
+    omaha_request_params_->set_wall_clock_based_wait_enabled(false);
+    omaha_request_params_->set_update_check_count_wait_enabled(false);
+    omaha_request_params_->set_waiting_period(TimeDelta::FromSeconds(0));
+    prefs_->Delete(kPrefsWallClockWaitPeriod);
+    prefs_->Delete(kPrefsUpdateCheckCount);
+    // Don't delete the UpdateFirstSeenAt file as we don't want manual checks
+    // that result in no-updates (e.g. due to server side throttling) to
+    // cause update starvation by having the client generate a new
+    // UpdateFirstSeenAt for each scheduled check that follows a manual check.
+  }
+}
+
+void UpdateAttempter::GenerateNewWaitingPeriod() {
+  omaha_request_params_->set_waiting_period(TimeDelta::FromSeconds(
+      base::RandInt(1, scatter_factor_.InSeconds())));
+
+  LOG(INFO) << "Generated new wall-clock waiting period: " << utils::FormatSecs(
+                omaha_request_params_->waiting_period().InSeconds());
+
+  // Do a best-effort to persist this in all cases. Even if the persistence
+  // fails, we'll still be able to scatter based on our in-memory value.
+  // The persistence only helps in ensuring a good overall distribution
+  // across multiple devices if they tend to reboot too often.
+  system_state_->payload_state()->SetScatteringWaitPeriod(
+      omaha_request_params_->waiting_period());
+}
+
+void UpdateAttempter::BuildPostInstallActions(
+    InstallPlanAction* previous_action) {
+  shared_ptr<PostinstallRunnerAction> postinstall_runner_action(
+      new PostinstallRunnerAction(system_state_->boot_control()));
+  actions_.push_back(shared_ptr<AbstractAction>(postinstall_runner_action));
+  BondActions(previous_action,
+              postinstall_runner_action.get());
+}
+
+void UpdateAttempter::BuildUpdateActions(bool interactive) {
+  CHECK(!processor_->IsRunning());
+  processor_->set_delegate(this);
+
+  // Actions:
+  std::unique_ptr<LibcurlHttpFetcher> update_check_fetcher(
+      new LibcurlHttpFetcher(GetProxyResolver(), system_state_->hardware()));
+  update_check_fetcher->set_server_to_check(ServerToCheck::kUpdate);
+  // Try harder to connect to the network, esp when not interactive.
+  // See comment in libcurl_http_fetcher.cc.
+  update_check_fetcher->set_no_network_max_retries(interactive ? 1 : 3);
+  shared_ptr<OmahaRequestAction> update_check_action(
+      new OmahaRequestAction(system_state_,
+                             nullptr,
+                             std::move(update_check_fetcher),
+                             false));
+  shared_ptr<OmahaResponseHandlerAction> response_handler_action(
+      new OmahaResponseHandlerAction(system_state_));
+  shared_ptr<FilesystemVerifierAction> src_filesystem_verifier_action(
+      new FilesystemVerifierAction(system_state_->boot_control(),
+                                   VerifierMode::kComputeSourceHash));
+
+  shared_ptr<OmahaRequestAction> download_started_action(
+      new OmahaRequestAction(system_state_,
+                             new OmahaEvent(
+                                 OmahaEvent::kTypeUpdateDownloadStarted),
+                             brillo::make_unique_ptr(new LibcurlHttpFetcher(
+                                 GetProxyResolver(),
+                                 system_state_->hardware())),
+                             false));
+
+  LibcurlHttpFetcher* download_fetcher =
+      new LibcurlHttpFetcher(GetProxyResolver(), system_state_->hardware());
+  download_fetcher->set_server_to_check(ServerToCheck::kDownload);
+  shared_ptr<DownloadAction> download_action(
+      new DownloadAction(prefs_,
+                         system_state_,
+                         new MultiRangeHttpFetcher(
+                             download_fetcher)));  // passes ownership
+  shared_ptr<OmahaRequestAction> download_finished_action(
+      new OmahaRequestAction(
+          system_state_,
+          new OmahaEvent(OmahaEvent::kTypeUpdateDownloadFinished),
+          brillo::make_unique_ptr(
+              new LibcurlHttpFetcher(GetProxyResolver(),
+                                     system_state_->hardware())),
+          false));
+  shared_ptr<FilesystemVerifierAction> dst_filesystem_verifier_action(
+      new FilesystemVerifierAction(system_state_->boot_control(),
+                                   VerifierMode::kVerifyTargetHash));
+  shared_ptr<OmahaRequestAction> update_complete_action(
+      new OmahaRequestAction(
+          system_state_,
+          new OmahaEvent(OmahaEvent::kTypeUpdateComplete),
+          brillo::make_unique_ptr(
+              new LibcurlHttpFetcher(GetProxyResolver(),
+                                     system_state_->hardware())),
+          false));
+
+  download_action->set_delegate(this);
+  response_handler_action_ = response_handler_action;
+  download_action_ = download_action;
+
+  actions_.push_back(shared_ptr<AbstractAction>(update_check_action));
+  actions_.push_back(shared_ptr<AbstractAction>(response_handler_action));
+  actions_.push_back(shared_ptr<AbstractAction>(
+      src_filesystem_verifier_action));
+  actions_.push_back(shared_ptr<AbstractAction>(download_started_action));
+  actions_.push_back(shared_ptr<AbstractAction>(download_action));
+  actions_.push_back(shared_ptr<AbstractAction>(download_finished_action));
+  actions_.push_back(shared_ptr<AbstractAction>(
+      dst_filesystem_verifier_action));
+
+  // Bond them together. We have to use the leaf-types when calling
+  // BondActions().
+  BondActions(update_check_action.get(),
+              response_handler_action.get());
+  BondActions(response_handler_action.get(),
+              src_filesystem_verifier_action.get());
+  BondActions(src_filesystem_verifier_action.get(),
+              download_action.get());
+  BondActions(download_action.get(),
+              dst_filesystem_verifier_action.get());
+  BuildPostInstallActions(dst_filesystem_verifier_action.get());
+
+  actions_.push_back(shared_ptr<AbstractAction>(update_complete_action));
+
+  // Enqueue the actions
+  for (const shared_ptr<AbstractAction>& action : actions_) {
+    processor_->EnqueueAction(action.get());
+  }
+}
+
+bool UpdateAttempter::Rollback(bool powerwash) {
+  if (!CanRollback()) {
+    return false;
+  }
+
+  // Extra check for enterprise-enrolled devices since they don't support
+  // powerwash.
+  if (powerwash) {
+    // Enterprise-enrolled devices have an empty owner in their device policy.
+    string owner;
+    RefreshDevicePolicy();
+    const policy::DevicePolicy* device_policy = system_state_->device_policy();
+    if (device_policy && (!device_policy->GetOwner(&owner) || owner.empty())) {
+      LOG(ERROR) << "Enterprise device detected. "
+                 << "Cannot perform a powerwash for enterprise devices.";
+      return false;
+    }
+  }
+
+  processor_->set_delegate(this);
+
+  // Initialize the default request params.
+  if (!omaha_request_params_->Init("", "", true)) {
+    LOG(ERROR) << "Unable to initialize Omaha request params.";
+    return false;
+  }
+
+  LOG(INFO) << "Setting rollback options.";
+  InstallPlan install_plan;
+
+  install_plan.target_slot = GetRollbackSlot();
+  install_plan.source_slot = system_state_->boot_control()->GetCurrentSlot();
+
+  TEST_AND_RETURN_FALSE(
+      install_plan.LoadPartitionsFromSlots(system_state_->boot_control()));
+  install_plan.powerwash_required = powerwash;
+
+  LOG(INFO) << "Using this install plan:";
+  install_plan.Dump();
+
+  shared_ptr<InstallPlanAction> install_plan_action(
+      new InstallPlanAction(install_plan));
+  actions_.push_back(shared_ptr<AbstractAction>(install_plan_action));
+
+  BuildPostInstallActions(install_plan_action.get());
+
+  // Enqueue the actions
+  for (const shared_ptr<AbstractAction>& action : actions_) {
+    processor_->EnqueueAction(action.get());
+  }
+
+  // Update the payload state for Rollback.
+  system_state_->payload_state()->Rollback();
+
+  SetStatusAndNotify(UpdateStatus::ATTEMPTING_ROLLBACK);
+
+  // Just in case we didn't update boot flags yet, make sure they're updated
+  // before any update processing starts. This also schedules the start of the
+  // actions we just posted.
+  start_action_processor_ = true;
+  UpdateBootFlags();
+  return true;
+}
+
+bool UpdateAttempter::CanRollback() const {
+  // We can only rollback if the update_engine isn't busy and we have a valid
+  // rollback partition.
+  return (status_ == UpdateStatus::IDLE &&
+          GetRollbackSlot() != BootControlInterface::kInvalidSlot);
+}
+
+BootControlInterface::Slot UpdateAttempter::GetRollbackSlot() const {
+  LOG(INFO) << "UpdateAttempter::GetRollbackSlot";
+  const unsigned int num_slots = system_state_->boot_control()->GetNumSlots();
+  const BootControlInterface::Slot current_slot =
+      system_state_->boot_control()->GetCurrentSlot();
+
+  LOG(INFO) << "  Installed slots: " << num_slots;
+  LOG(INFO) << "  Booted from slot: "
+            << BootControlInterface::SlotName(current_slot);
+
+  if (current_slot == BootControlInterface::kInvalidSlot || num_slots < 2) {
+    LOG(INFO) << "Device is not updateable.";
+    return BootControlInterface::kInvalidSlot;
+  }
+
+  vector<BootControlInterface::Slot> bootable_slots;
+  for(BootControlInterface::Slot slot = 0; slot < num_slots; slot++) {
+    if (slot != current_slot &&
+        system_state_->boot_control()->IsSlotBootable(slot)) {
+      LOG(INFO) << "Found bootable slot "
+                << BootControlInterface::SlotName(slot);
+      return slot;
+    }
+  }
+  LOG(INFO) << "No other bootable slot found.";
+  return BootControlInterface::kInvalidSlot;
+}
+
+void UpdateAttempter::CheckForUpdate(const string& app_version,
+                                     const string& omaha_url,
+                                     bool interactive) {
+  LOG(INFO) << "Forced update check requested.";
+  forced_app_version_.clear();
+  forced_omaha_url_.clear();
+
+  // Certain conditions must be met to allow setting custom version and update
+  // server URLs. However, kScheduledAUTestURLRequest and kAUTestURLRequest are
+  // always allowed regardless of device state.
+  if (IsAnyUpdateSourceAllowed()) {
+    forced_app_version_ = app_version;
+    forced_omaha_url_ = omaha_url;
+  }
+  if (omaha_url == kScheduledAUTestURLRequest) {
+    forced_omaha_url_ = constants::kOmahaDefaultAUTestURL;
+    // Pretend that it's not user-initiated even though it is,
+    // so as to test scattering logic, etc. which get kicked off
+    // only in scheduled update checks.
+    interactive = false;
+  } else if (omaha_url == kAUTestURLRequest) {
+    forced_omaha_url_ = constants::kOmahaDefaultAUTestURL;
+  }
+
+  if (forced_update_pending_callback_.get()) {
+    // Make sure that a scheduling request is made prior to calling the forced
+    // update pending callback.
+    ScheduleUpdates();
+    forced_update_pending_callback_->Run(true, interactive);
+  }
+}
+
+bool UpdateAttempter::RebootIfNeeded() {
+  if (status_ != UpdateStatus::UPDATED_NEED_REBOOT) {
+    LOG(INFO) << "Reboot requested, but status is "
+              << UpdateStatusToString(status_) << ", so not rebooting.";
+    return false;
+  }
+
+  if (USE_POWER_MANAGEMENT && RequestPowerManagerReboot())
+    return true;
+
+  return RebootDirectly();
+}
+
+void UpdateAttempter::WriteUpdateCompletedMarker() {
+  string boot_id;
+  if (!utils::GetBootId(&boot_id))
+    return;
+  prefs_->SetString(kPrefsUpdateCompletedOnBootId, boot_id);
+
+  int64_t value = system_state_->clock()->GetBootTime().ToInternalValue();
+  prefs_->SetInt64(kPrefsUpdateCompletedBootTime, value);
+}
+
+bool UpdateAttempter::RequestPowerManagerReboot() {
+  org::chromium::PowerManagerProxyInterface* power_manager_proxy =
+      system_state_->power_manager_proxy();
+  if (!power_manager_proxy) {
+    LOG(WARNING) << "No PowerManager proxy defined, skipping reboot.";
+    return false;
+  }
+  LOG(INFO) << "Calling " << power_manager::kPowerManagerInterface << "."
+            << power_manager::kRequestRestartMethod;
+  brillo::ErrorPtr error;
+  return power_manager_proxy->RequestRestart(
+      power_manager::REQUEST_RESTART_FOR_UPDATE, &error);
+}
+
+bool UpdateAttempter::RebootDirectly() {
+  vector<string> command;
+  command.push_back("/sbin/shutdown");
+  command.push_back("-r");
+  command.push_back("now");
+  LOG(INFO) << "Running \"" << JoinString(command, ' ') << "\"";
+  int rc = 0;
+  Subprocess::SynchronousExec(command, &rc, nullptr);
+  return rc == 0;
+}
+
+void UpdateAttempter::OnUpdateScheduled(EvalStatus status,
+                                        const UpdateCheckParams& params) {
+  waiting_for_scheduled_check_ = false;
+
+  if (status == EvalStatus::kSucceeded) {
+    if (!params.updates_enabled) {
+      LOG(WARNING) << "Updates permanently disabled.";
+      // Signal disabled status, then switch right back to idle. This is
+      // necessary for ensuring that observers waiting for a signal change will
+      // actually notice one on subsequent calls. Note that we don't need to
+      // re-schedule a check in this case as updates are permanently disabled;
+      // further (forced) checks may still initiate a scheduling call.
+      SetStatusAndNotify(UpdateStatus::DISABLED);
+      SetStatusAndNotify(UpdateStatus::IDLE);
+      return;
+    }
+
+    LOG(INFO) << "Running "
+              << (params.is_interactive ? "interactive" : "periodic")
+              << " update.";
+
+    string app_version, omaha_url;
+    if (params.is_interactive) {
+      app_version = forced_app_version_;
+      omaha_url = forced_omaha_url_;
+    }
+
+    Update(app_version, omaha_url, params.target_channel,
+           params.target_version_prefix, false, params.is_interactive);
+  } else {
+    LOG(WARNING)
+        << "Update check scheduling failed (possibly timed out); retrying.";
+    ScheduleUpdates();
+  }
+
+  // This check ensures that future update checks will be or are already
+  // scheduled. The check should never fail. A check failure means that there's
+  // a bug that will most likely prevent further automatic update checks. It
+  // seems better to crash in such cases and restart the update_engine daemon
+  // into, hopefully, a known good state.
+  CHECK(IsUpdateRunningOrScheduled());
+}
+
+void UpdateAttempter::UpdateLastCheckedTime() {
+  last_checked_time_ = system_state_->clock()->GetWallclockTime().ToTimeT();
+}
+
+// Delegate methods:
+void UpdateAttempter::ProcessingDone(const ActionProcessor* processor,
+                                     ErrorCode code) {
+  LOG(INFO) << "Processing Done.";
+  actions_.clear();
+
+  // Reset cpu shares back to normal.
+  CleanupCpuSharesManagement();
+
+  if (status_ == UpdateStatus::REPORTING_ERROR_EVENT) {
+    LOG(INFO) << "Error event sent.";
+
+    // Inform scheduler of new status;
+    SetStatusAndNotify(UpdateStatus::IDLE);
+    ScheduleUpdates();
+
+    if (!fake_update_success_) {
+      return;
+    }
+    LOG(INFO) << "Booted from FW B and tried to install new firmware, "
+        "so requesting reboot from user.";
+  }
+
+  if (code == ErrorCode::kSuccess) {
+    WriteUpdateCompletedMarker();
+    prefs_->SetInt64(kPrefsDeltaUpdateFailures, 0);
+    prefs_->SetString(kPrefsPreviousVersion,
+                      omaha_request_params_->app_version());
+    DeltaPerformer::ResetUpdateProgress(prefs_, false);
+
+    system_state_->payload_state()->UpdateSucceeded();
+
+    // Since we're done with scattering fully at this point, this is the
+    // safest point delete the state files, as we're sure that the status is
+    // set to reboot (which means no more updates will be applied until reboot)
+    // This deletion is required for correctness as we want the next update
+    // check to re-create a new random number for the update check count.
+    // Similarly, we also delete the wall-clock-wait period that was persisted
+    // so that we start with a new random value for the next update check
+    // after reboot so that the same device is not favored or punished in any
+    // way.
+    prefs_->Delete(kPrefsUpdateCheckCount);
+    system_state_->payload_state()->SetScatteringWaitPeriod(TimeDelta());
+    prefs_->Delete(kPrefsUpdateFirstSeenAt);
+
+    SetStatusAndNotify(UpdateStatus::UPDATED_NEED_REBOOT);
+    ScheduleUpdates();
+    LOG(INFO) << "Update successfully applied, waiting to reboot.";
+
+    // This pointer is null during rollback operations, and the stats
+    // don't make much sense then anyway.
+    if (response_handler_action_) {
+      const InstallPlan& install_plan =
+          response_handler_action_->install_plan();
+
+      // Generate an unique payload identifier.
+      const string target_version_uid =
+          install_plan.payload_hash + ":" + install_plan.metadata_signature;
+
+      // Expect to reboot into the new version to send the proper metric during
+      // next boot.
+      system_state_->payload_state()->ExpectRebootInNewVersion(
+          target_version_uid);
+    } else {
+      // If we just finished a rollback, then we expect to have no Omaha
+      // response. Otherwise, it's an error.
+      if (system_state_->payload_state()->GetRollbackVersion().empty()) {
+        LOG(ERROR) << "Can't send metrics because expected "
+            "response_handler_action_ missing.";
+      }
+    }
+    return;
+  }
+
+  if (ScheduleErrorEventAction()) {
+    return;
+  }
+  LOG(INFO) << "No update.";
+  SetStatusAndNotify(UpdateStatus::IDLE);
+  ScheduleUpdates();
+}
+
+void UpdateAttempter::ProcessingStopped(const ActionProcessor* processor) {
+  // Reset cpu shares back to normal.
+  CleanupCpuSharesManagement();
+  download_progress_ = 0.0;
+  SetStatusAndNotify(UpdateStatus::IDLE);
+  ScheduleUpdates();
+  actions_.clear();
+  error_event_.reset(nullptr);
+}
+
+// Called whenever an action has finished processing, either successfully
+// or otherwise.
+void UpdateAttempter::ActionCompleted(ActionProcessor* processor,
+                                      AbstractAction* action,
+                                      ErrorCode code) {
+  // Reset download progress regardless of whether or not the download
+  // action succeeded. Also, get the response code from HTTP request
+  // actions (update download as well as the initial update check
+  // actions).
+  const string type = action->Type();
+  if (type == DownloadAction::StaticType()) {
+    download_progress_ = 0.0;
+    DownloadAction* download_action = static_cast<DownloadAction*>(action);
+    http_response_code_ = download_action->GetHTTPResponseCode();
+  } else if (type == OmahaRequestAction::StaticType()) {
+    OmahaRequestAction* omaha_request_action =
+        static_cast<OmahaRequestAction*>(action);
+    // If the request is not an event, then it's the update-check.
+    if (!omaha_request_action->IsEvent()) {
+      http_response_code_ = omaha_request_action->GetHTTPResponseCode();
+
+      // Record the number of consecutive failed update checks.
+      if (http_response_code_ == kHttpResponseInternalServerError ||
+          http_response_code_ == kHttpResponseServiceUnavailable) {
+        consecutive_failed_update_checks_++;
+      } else {
+        consecutive_failed_update_checks_ = 0;
+      }
+
+      // Store the server-dictated poll interval, if any.
+      server_dictated_poll_interval_ =
+          std::max(0, omaha_request_action->GetOutputObject().poll_interval);
+    }
+  }
+  if (code != ErrorCode::kSuccess) {
+    // If the current state is at or past the download phase, count the failure
+    // in case a switch to full update becomes necessary. Ignore network
+    // transfer timeouts and failures.
+    if (status_ >= UpdateStatus::DOWNLOADING &&
+        code != ErrorCode::kDownloadTransferError) {
+      MarkDeltaUpdateFailure();
+    }
+    // On failure, schedule an error event to be sent to Omaha.
+    CreatePendingErrorEvent(action, code);
+    return;
+  }
+  // Find out which action completed.
+  if (type == OmahaResponseHandlerAction::StaticType()) {
+    // Note that the status will be updated to DOWNLOADING when some bytes get
+    // actually downloaded from the server and the BytesReceived callback is
+    // invoked. This avoids notifying the user that a download has started in
+    // cases when the server and the client are unable to initiate the download.
+    CHECK(action == response_handler_action_.get());
+    const InstallPlan& plan = response_handler_action_->install_plan();
+    UpdateLastCheckedTime();
+    new_version_ = plan.version;
+    new_payload_size_ = plan.payload_size;
+    SetupDownload();
+    SetupCpuSharesManagement();
+    SetStatusAndNotify(UpdateStatus::UPDATE_AVAILABLE);
+  } else if (type == DownloadAction::StaticType()) {
+    SetStatusAndNotify(UpdateStatus::FINALIZING);
+  }
+}
+
+void UpdateAttempter::BytesReceived(uint64_t bytes_progressed,
+                                    uint64_t bytes_received,
+                                    uint64_t total) {
+  // The PayloadState keeps track of how many bytes were actually downloaded
+  // from a given URL for the URL skipping logic.
+  system_state_->payload_state()->DownloadProgress(bytes_progressed);
+
+  double progress = static_cast<double>(bytes_received) /
+      static_cast<double>(total);
+  // Self throttle based on progress. Also send notifications if
+  // progress is too slow.
+  const double kDeltaPercent = 0.01;  // 1%
+  if (status_ != UpdateStatus::DOWNLOADING ||
+      bytes_received == total ||
+      progress - download_progress_ >= kDeltaPercent ||
+      TimeTicks::Now() - last_notify_time_ >= TimeDelta::FromSeconds(10)) {
+    download_progress_ = progress;
+    SetStatusAndNotify(UpdateStatus::DOWNLOADING);
+  }
+}
+
+void UpdateAttempter::DownloadComplete() {
+  system_state_->payload_state()->DownloadComplete();
+}
+
+bool UpdateAttempter::ResetStatus() {
+  LOG(INFO) << "Attempting to reset state from "
+            << UpdateStatusToString(status_) << " to UpdateStatus::IDLE";
+
+  switch (status_) {
+    case UpdateStatus::IDLE:
+      // no-op.
+      return true;
+
+    case UpdateStatus::UPDATED_NEED_REBOOT:  {
+      bool ret_value = true;
+      status_ = UpdateStatus::IDLE;
+
+      // Remove the reboot marker so that if the machine is rebooted
+      // after resetting to idle state, it doesn't go back to
+      // UpdateStatus::UPDATED_NEED_REBOOT state.
+      ret_value = prefs_->Delete(kPrefsUpdateCompletedOnBootId) && ret_value;
+      ret_value = prefs_->Delete(kPrefsUpdateCompletedBootTime) && ret_value;
+
+      // Update the boot flags so the current slot has higher priority.
+      BootControlInterface* boot_control = system_state_->boot_control();
+      if (!boot_control->SetActiveBootSlot(boot_control->GetCurrentSlot()))
+        ret_value = false;
+
+      // Notify the PayloadState that the successful payload was canceled.
+      system_state_->payload_state()->ResetUpdateStatus();
+
+      // The previous version is used to report back to omaha after reboot that
+      // we actually rebooted into the new version from this "prev-version". We
+      // need to clear out this value now to prevent it being sent on the next
+      // updatecheck request.
+      ret_value = prefs_->SetString(kPrefsPreviousVersion, "") && ret_value;
+
+      LOG(INFO) << "Reset status " << (ret_value ? "successful" : "failed");
+      return ret_value;
+    }
+
+    default:
+      LOG(ERROR) << "Reset not allowed in this state.";
+      return false;
+  }
+}
+
+bool UpdateAttempter::GetStatus(int64_t* last_checked_time,
+                                double* progress,
+                                string* current_operation,
+                                string* new_version,
+                                int64_t* new_payload_size) {
+  *last_checked_time = last_checked_time_;
+  *progress = download_progress_;
+  *current_operation = UpdateStatusToString(status_);
+  *new_version = new_version_;
+  *new_payload_size = new_payload_size_;
+  return true;
+}
+
+void UpdateAttempter::UpdateBootFlags() {
+  if (update_boot_flags_running_) {
+    LOG(INFO) << "Update boot flags running, nothing to do.";
+    return;
+  }
+  if (updated_boot_flags_) {
+    LOG(INFO) << "Already updated boot flags. Skipping.";
+    if (start_action_processor_) {
+      ScheduleProcessingStart();
+    }
+    return;
+  }
+  // This is purely best effort. Failures should be logged by Subprocess. Run
+  // the script asynchronously to avoid blocking the event loop regardless of
+  // the script runtime.
+  update_boot_flags_running_ = true;
+  LOG(INFO) << "Marking booted slot as good.";
+  if (!system_state_->boot_control()->MarkBootSuccessfulAsync(Bind(
+          &UpdateAttempter::CompleteUpdateBootFlags, base::Unretained(this)))) {
+    LOG(ERROR) << "Failed to mark current boot as successful.";
+    CompleteUpdateBootFlags(false);
+  }
+}
+
+void UpdateAttempter::CompleteUpdateBootFlags(bool successful) {
+  update_boot_flags_running_ = false;
+  updated_boot_flags_ = true;
+  if (start_action_processor_) {
+    ScheduleProcessingStart();
+  }
+}
+
+void UpdateAttempter::BroadcastStatus() {
+  if (!dbus_adaptor_)
+    return;
+  last_notify_time_ = TimeTicks::Now();
+  dbus_adaptor_->SendStatusUpdateSignal(
+      last_checked_time_,
+      download_progress_,
+      UpdateStatusToString(status_),
+      new_version_.c_str(),
+      new_payload_size_);
+}
+
+uint32_t UpdateAttempter::GetErrorCodeFlags()  {
+  uint32_t flags = 0;
+
+  if (!system_state_->hardware()->IsNormalBootMode())
+    flags |= static_cast<uint32_t>(ErrorCode::kDevModeFlag);
+
+  if (response_handler_action_.get() &&
+      response_handler_action_->install_plan().is_resume)
+    flags |= static_cast<uint32_t>(ErrorCode::kResumedFlag);
+
+  if (!system_state_->hardware()->IsOfficialBuild())
+    flags |= static_cast<uint32_t>(ErrorCode::kTestImageFlag);
+
+  if (omaha_request_params_->update_url() !=
+      constants::kOmahaDefaultProductionURL) {
+    flags |= static_cast<uint32_t>(ErrorCode::kTestOmahaUrlFlag);
+  }
+
+  return flags;
+}
+
+bool UpdateAttempter::ShouldCancel(ErrorCode* cancel_reason) {
+  // Check if the channel we're attempting to update to is the same as the
+  // target channel currently chosen by the user.
+  OmahaRequestParams* params = system_state_->request_params();
+  if (params->download_channel() != params->target_channel()) {
+    LOG(ERROR) << "Aborting download as target channel: "
+               << params->target_channel()
+               << " is different from the download channel: "
+               << params->download_channel();
+    *cancel_reason = ErrorCode::kUpdateCanceledByChannelChange;
+    return true;
+  }
+
+  return false;
+}
+
+void UpdateAttempter::SetStatusAndNotify(UpdateStatus status) {
+  status_ = status;
+  BroadcastStatus();
+}
+
+void UpdateAttempter::CreatePendingErrorEvent(AbstractAction* action,
+                                              ErrorCode code) {
+  if (error_event_.get()) {
+    // This shouldn't really happen.
+    LOG(WARNING) << "There's already an existing pending error event.";
+    return;
+  }
+
+  // For now assume that a generic Omaha response action failure means that
+  // there's no update so don't send an event. Also, double check that the
+  // failure has not occurred while sending an error event -- in which case
+  // don't schedule another. This shouldn't really happen but just in case...
+  if ((action->Type() == OmahaResponseHandlerAction::StaticType() &&
+       code == ErrorCode::kError) ||
+      status_ == UpdateStatus::REPORTING_ERROR_EVENT) {
+    return;
+  }
+
+  // Classify the code to generate the appropriate result so that
+  // the Borgmon charts show up the results correctly.
+  // Do this before calling GetErrorCodeForAction which could potentially
+  // augment the bit representation of code and thus cause no matches for
+  // the switch cases below.
+  OmahaEvent::Result event_result;
+  switch (code) {
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+      event_result = OmahaEvent::kResultUpdateDeferred;
+      break;
+    default:
+      event_result = OmahaEvent::kResultError;
+      break;
+  }
+
+  code = GetErrorCodeForAction(action, code);
+  fake_update_success_ = code == ErrorCode::kPostinstallBootedFromFirmwareB;
+
+  // Compute the final error code with all the bit flags to be sent to Omaha.
+  code = static_cast<ErrorCode>(
+      static_cast<uint32_t>(code) | GetErrorCodeFlags());
+  error_event_.reset(new OmahaEvent(OmahaEvent::kTypeUpdateComplete,
+                                    event_result,
+                                    code));
+}
+
+bool UpdateAttempter::ScheduleErrorEventAction() {
+  if (error_event_.get() == nullptr)
+    return false;
+
+  LOG(ERROR) << "Update failed.";
+  system_state_->payload_state()->UpdateFailed(error_event_->error_code);
+
+  // Send it to Omaha.
+  LOG(INFO) << "Reporting the error event";
+  shared_ptr<OmahaRequestAction> error_event_action(
+      new OmahaRequestAction(system_state_,
+                             error_event_.release(),  // Pass ownership.
+                             brillo::make_unique_ptr(new LibcurlHttpFetcher(
+                                 GetProxyResolver(),
+                                 system_state_->hardware())),
+                             false));
+  actions_.push_back(shared_ptr<AbstractAction>(error_event_action));
+  processor_->EnqueueAction(error_event_action.get());
+  SetStatusAndNotify(UpdateStatus::REPORTING_ERROR_EVENT);
+  processor_->StartProcessing();
+  return true;
+}
+
+void UpdateAttempter::SetCpuShares(utils::CpuShares shares) {
+  if (shares_ == shares) {
+    return;
+  }
+  if (utils::SetCpuShares(shares)) {
+    shares_ = shares;
+    LOG(INFO) << "CPU shares = " << shares_;
+  }
+}
+
+void UpdateAttempter::SetupCpuSharesManagement() {
+  if (manage_shares_id_ != MessageLoop::kTaskIdNull) {
+    LOG(ERROR) << "Cpu shares timeout source hasn't been destroyed.";
+    CleanupCpuSharesManagement();
+  }
+  const int kCpuSharesTimeout = 2 * 60 * 60;  // 2 hours
+  manage_shares_id_ = MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      Bind(&UpdateAttempter::ManageCpuSharesCallback, base::Unretained(this)),
+      TimeDelta::FromSeconds(kCpuSharesTimeout));
+  SetCpuShares(utils::kCpuSharesLow);
+}
+
+void UpdateAttempter::CleanupCpuSharesManagement() {
+  if (manage_shares_id_ != MessageLoop::kTaskIdNull) {
+    // The UpdateAttempter is instantiated by default by the FakeSystemState,
+    // even when it is not used. We check the manage_shares_id_ before calling
+    // the MessageLoop::current() since the unit test using a FakeSystemState
+    // may have not define a MessageLoop for the current thread.
+    MessageLoop::current()->CancelTask(manage_shares_id_);
+    manage_shares_id_ = MessageLoop::kTaskIdNull;
+  }
+  SetCpuShares(utils::kCpuSharesNormal);
+}
+
+void UpdateAttempter::ScheduleProcessingStart() {
+  LOG(INFO) << "Scheduling an action processor start.";
+  start_action_processor_ = false;
+  MessageLoop::current()->PostTask(
+      FROM_HERE,
+      Bind([this] { this->processor_->StartProcessing(); }));
+}
+
+void UpdateAttempter::ManageCpuSharesCallback() {
+  SetCpuShares(utils::kCpuSharesNormal);
+  manage_shares_id_ = MessageLoop::kTaskIdNull;
+}
+
+void UpdateAttempter::DisableDeltaUpdateIfNeeded() {
+  int64_t delta_failures;
+  if (omaha_request_params_->delta_okay() &&
+      prefs_->GetInt64(kPrefsDeltaUpdateFailures, &delta_failures) &&
+      delta_failures >= kMaxDeltaUpdateFailures) {
+    LOG(WARNING) << "Too many delta update failures, forcing full update.";
+    omaha_request_params_->set_delta_okay(false);
+  }
+}
+
+void UpdateAttempter::MarkDeltaUpdateFailure() {
+  // Don't try to resume a failed delta update.
+  DeltaPerformer::ResetUpdateProgress(prefs_, false);
+  int64_t delta_failures;
+  if (!prefs_->GetInt64(kPrefsDeltaUpdateFailures, &delta_failures) ||
+      delta_failures < 0) {
+    delta_failures = 0;
+  }
+  prefs_->SetInt64(kPrefsDeltaUpdateFailures, ++delta_failures);
+}
+
+void UpdateAttempter::SetupDownload() {
+  MultiRangeHttpFetcher* fetcher =
+      static_cast<MultiRangeHttpFetcher*>(download_action_->http_fetcher());
+  fetcher->ClearRanges();
+  if (response_handler_action_->install_plan().is_resume) {
+    // Resuming an update so fetch the update manifest metadata first.
+    int64_t manifest_metadata_size = 0;
+    prefs_->GetInt64(kPrefsManifestMetadataSize, &manifest_metadata_size);
+    fetcher->AddRange(0, manifest_metadata_size);
+    // If there're remaining unprocessed data blobs, fetch them. Be careful not
+    // to request data beyond the end of the payload to avoid 416 HTTP response
+    // error codes.
+    int64_t next_data_offset = 0;
+    prefs_->GetInt64(kPrefsUpdateStateNextDataOffset, &next_data_offset);
+    uint64_t resume_offset = manifest_metadata_size + next_data_offset;
+    if (resume_offset < response_handler_action_->install_plan().payload_size) {
+      fetcher->AddRange(resume_offset);
+    }
+  } else {
+    fetcher->AddRange(0);
+  }
+}
+
+void UpdateAttempter::PingOmaha() {
+  if (!processor_->IsRunning()) {
+    shared_ptr<OmahaRequestAction> ping_action(new OmahaRequestAction(
+        system_state_,
+        nullptr,
+        brillo::make_unique_ptr(new LibcurlHttpFetcher(
+            GetProxyResolver(),
+            system_state_->hardware())),
+        true));
+    actions_.push_back(shared_ptr<OmahaRequestAction>(ping_action));
+    processor_->set_delegate(nullptr);
+    processor_->EnqueueAction(ping_action.get());
+    // Call StartProcessing() synchronously here to avoid any race conditions
+    // caused by multiple outstanding ping Omaha requests.  If we call
+    // StartProcessing() asynchronously, the device can be suspended before we
+    // get a chance to callback to StartProcessing().  When the device resumes
+    // (assuming the device sleeps longer than the next update check period),
+    // StartProcessing() is called back and at the same time, the next update
+    // check is fired which eventually invokes StartProcessing().  A crash
+    // can occur because StartProcessing() checks to make sure that the
+    // processor is idle which it isn't due to the two concurrent ping Omaha
+    // requests.
+    processor_->StartProcessing();
+  } else {
+    LOG(WARNING) << "Action processor running, Omaha ping suppressed.";
+  }
+
+  // Update the last check time here; it may be re-updated when an Omaha
+  // response is received, but this will prevent us from repeatedly scheduling
+  // checks in the case where a response is not received.
+  UpdateLastCheckedTime();
+
+  // Update the status which will schedule the next update check
+  SetStatusAndNotify(UpdateStatus::UPDATED_NEED_REBOOT);
+  ScheduleUpdates();
+}
+
+
+bool UpdateAttempter::DecrementUpdateCheckCount() {
+  int64_t update_check_count_value;
+
+  if (!prefs_->Exists(kPrefsUpdateCheckCount)) {
+    // This file does not exist. This means we haven't started our update
+    // check count down yet, so nothing more to do. This file will be created
+    // later when we first satisfy the wall-clock-based-wait period.
+    LOG(INFO) << "No existing update check count. That's normal.";
+    return true;
+  }
+
+  if (prefs_->GetInt64(kPrefsUpdateCheckCount, &update_check_count_value)) {
+    // Only if we're able to read a proper integer value, then go ahead
+    // and decrement and write back the result in the same file, if needed.
+    LOG(INFO) << "Update check count = " << update_check_count_value;
+
+    if (update_check_count_value == 0) {
+      // It could be 0, if, for some reason, the file didn't get deleted
+      // when we set our status to waiting for reboot. so we just leave it
+      // as is so that we can prevent another update_check wait for this client.
+      LOG(INFO) << "Not decrementing update check count as it's already 0.";
+      return true;
+    }
+
+    if (update_check_count_value > 0)
+      update_check_count_value--;
+    else
+      update_check_count_value = 0;
+
+    // Write out the new value of update_check_count_value.
+    if (prefs_->SetInt64(kPrefsUpdateCheckCount, update_check_count_value)) {
+      // We successfully wrote out te new value, so enable the
+      // update check based wait.
+      LOG(INFO) << "New update check count = " << update_check_count_value;
+      return true;
+    }
+  }
+
+  LOG(INFO) << "Deleting update check count state due to read/write errors.";
+
+  // We cannot read/write to the file, so disable the update check based wait
+  // so that we don't get stuck in this OS version by any chance (which could
+  // happen if there's some bug that causes to read/write incorrectly).
+  // Also attempt to delete the file to do our best effort to cleanup.
+  prefs_->Delete(kPrefsUpdateCheckCount);
+  return false;
+}
+
+
+void UpdateAttempter::UpdateEngineStarted() {
+  // If we just booted into a new update, keep the previous OS version
+  // in case we rebooted because of a crash of the old version, so we
+  // can do a proper crash report with correct information.
+  // This must be done before calling
+  // system_state_->payload_state()->UpdateEngineStarted() since it will
+  // delete SystemUpdated marker file.
+  if (system_state_->system_rebooted() &&
+      prefs_->Exists(kPrefsSystemUpdatedMarker)) {
+    if (!prefs_->GetString(kPrefsPreviousVersion, &prev_version_)) {
+      // If we fail to get the version string, make sure it stays empty.
+      prev_version_.clear();
+    }
+  }
+
+  system_state_->payload_state()->UpdateEngineStarted();
+  StartP2PAtStartup();
+}
+
+bool UpdateAttempter::StartP2PAtStartup() {
+  if (system_state_ == nullptr ||
+      !system_state_->p2p_manager()->IsP2PEnabled()) {
+    LOG(INFO) << "Not starting p2p at startup since it's not enabled.";
+    return false;
+  }
+
+  if (system_state_->p2p_manager()->CountSharedFiles() < 1) {
+    LOG(INFO) << "Not starting p2p at startup since our application "
+              << "is not sharing any files.";
+    return false;
+  }
+
+  return StartP2PAndPerformHousekeeping();
+}
+
+bool UpdateAttempter::StartP2PAndPerformHousekeeping() {
+  if (system_state_ == nullptr)
+    return false;
+
+  if (!system_state_->p2p_manager()->IsP2PEnabled()) {
+    LOG(INFO) << "Not starting p2p since it's not enabled.";
+    return false;
+  }
+
+  LOG(INFO) << "Ensuring that p2p is running.";
+  if (!system_state_->p2p_manager()->EnsureP2PRunning()) {
+    LOG(ERROR) << "Error starting p2p.";
+    return false;
+  }
+
+  LOG(INFO) << "Performing p2p housekeeping.";
+  if (!system_state_->p2p_manager()->PerformHousekeeping()) {
+    LOG(ERROR) << "Error performing housekeeping for p2p.";
+    return false;
+  }
+
+  LOG(INFO) << "Done performing p2p housekeeping.";
+  return true;
+}
+
+bool UpdateAttempter::GetBootTimeAtUpdate(Time *out_boot_time) {
+  // In case of an update_engine restart without a reboot, we stored the boot_id
+  // when the update was completed by setting a pref, so we can check whether
+  // the last update was on this boot or a previous one.
+  string boot_id;
+  TEST_AND_RETURN_FALSE(utils::GetBootId(&boot_id));
+
+  string update_completed_on_boot_id;
+  if (!prefs_->Exists(kPrefsUpdateCompletedOnBootId) ||
+      !prefs_->GetString(kPrefsUpdateCompletedOnBootId,
+                         &update_completed_on_boot_id) ||
+      update_completed_on_boot_id != boot_id)
+    return false;
+
+  // Short-circuit avoiding the read in case out_boot_time is nullptr.
+  if (out_boot_time) {
+    int64_t boot_time = 0;
+    // Since the kPrefsUpdateCompletedOnBootId was correctly set, this pref
+    // should not fail.
+    TEST_AND_RETURN_FALSE(
+        prefs_->GetInt64(kPrefsUpdateCompletedBootTime, &boot_time));
+    *out_boot_time = Time::FromInternalValue(boot_time);
+  }
+  return true;
+}
+
+bool UpdateAttempter::IsUpdateRunningOrScheduled() {
+  return ((status_ != UpdateStatus::IDLE &&
+           status_ != UpdateStatus::UPDATED_NEED_REBOOT) ||
+          waiting_for_scheduled_check_);
+}
+
+bool UpdateAttempter::IsAnyUpdateSourceAllowed() {
+  // We allow updates from any source if either of these are true:
+  //  * The device is running an unofficial (dev/test) image.
+  //  * The debugd dev features are accessible (i.e. in devmode with no owner).
+  // This protects users running a base image, while still allowing a specific
+  // window (gated by the debug dev features) where `cros flash` is usable.
+  if (!system_state_->hardware()->IsOfficialBuild()) {
+    LOG(INFO) << "Non-official build; allowing any update source.";
+    return true;
+  }
+
+  // Even though the debugd tools are also gated on devmode, checking here can
+  // save us a D-Bus call so it's worth doing explicitly.
+  if (system_state_->hardware()->IsNormalBootMode()) {
+    LOG(INFO) << "Not in devmode; disallowing custom update sources.";
+    return false;
+  }
+
+  // Official images in devmode are allowed a custom update source iff the
+  // debugd dev tools are enabled.
+  if (!debugd_proxy_)
+    return false;
+  int32_t dev_features = debugd::DEV_FEATURES_DISABLED;
+  brillo::ErrorPtr error;
+  bool success = debugd_proxy_->QueryDevFeatures(&dev_features, &error);
+
+  // Some boards may not include debugd so it's expected that this may fail,
+  // in which case we default to disallowing custom update sources.
+  if (success && !(dev_features & debugd::DEV_FEATURES_DISABLED)) {
+    LOG(INFO) << "Debugd dev tools enabled; allowing any update source.";
+    return true;
+  }
+  LOG(INFO) << "Debugd dev tools disabled; disallowing custom update sources.";
+  return false;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/update_attempter.h b/update_attempter.h
new file mode 100644
index 0000000..cfe3e32
--- /dev/null
+++ b/update_attempter.h
@@ -0,0 +1,506 @@
+//
+// Copyright (C) 2012 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_ATTEMPTER_H_
+#define UPDATE_ENGINE_UPDATE_ATTEMPTER_H_
+
+#include <time.h>
+
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/time/time.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "debugd/dbus-proxies.h"
+#include "update_engine/chrome_browser_proxy_resolver.h"
+#include "update_engine/client_library/include/update_engine/update_status.h"
+#include "update_engine/common/action_processor.h"
+#include "update_engine/common/certificate_checker.h"
+#include "update_engine/libcros_proxy.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/omaha_response_handler_action.h"
+#include "update_engine/payload_consumer/download_action.h"
+#include "update_engine/proxy_resolver.h"
+#include "update_engine/system_state.h"
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/update_manager.h"
+
+class MetricsLibraryInterface;
+
+namespace policy {
+class PolicyProvider;
+}
+
+namespace chromeos_update_engine {
+
+class UpdateEngineAdaptor;
+
+class UpdateAttempter : public ActionProcessorDelegate,
+                        public DownloadActionDelegate,
+                        public CertificateChecker::Observer {
+ public:
+  using UpdateStatus = update_engine::UpdateStatus;
+  static const int kMaxDeltaUpdateFailures;
+
+  UpdateAttempter(SystemState* system_state,
+                  CertificateChecker* cert_checker,
+                  LibCrosProxy* libcros_proxy,
+                  org::chromium::debugdProxyInterface* debugd_proxy);
+  ~UpdateAttempter() override;
+
+  // Further initialization to be done post construction.
+  void Init();
+
+  // Initiates scheduling of update checks.
+  virtual void ScheduleUpdates();
+
+  // Checks for update and, if a newer version is available, attempts to update
+  // the system. Non-empty |in_app_version| or |in_update_url| prevents
+  // automatic detection of the parameter.  |target_channel| denotes a
+  // policy-mandated channel we are updating to, if not empty. If |obey_proxies|
+  // is true, the update will likely respect Chrome's proxy setting. For
+  // security reasons, we may still not honor them. |interactive| should be true
+  // if this was called from the user (ie dbus).
+  virtual void Update(const std::string& app_version,
+                      const std::string& omaha_url,
+                      const std::string& target_channel,
+                      const std::string& target_version_prefix,
+                      bool obey_proxies,
+                      bool interactive);
+
+  // ActionProcessorDelegate methods:
+  void ProcessingDone(const ActionProcessor* processor,
+                      ErrorCode code) override;
+  void ProcessingStopped(const ActionProcessor* processor) override;
+  void ActionCompleted(ActionProcessor* processor,
+                       AbstractAction* action,
+                       ErrorCode code) override;
+
+  // Resets the current state to UPDATE_STATUS_IDLE.
+  // Used by update_engine_client for restarting a new update without
+  // having to reboot once the previous update has reached
+  // UPDATE_STATUS_UPDATED_NEED_REBOOT state. This is used only
+  // for testing purposes.
+  virtual bool ResetStatus();
+
+  // Returns the current status in the out params. Returns true on success.
+  virtual bool GetStatus(int64_t* last_checked_time,
+                         double* progress,
+                         std::string* current_operation,
+                         std::string* new_version,
+                         int64_t* new_size);
+
+  // Runs chromeos-setgoodkernel, whose responsibility it is to mark the
+  // currently booted partition has high priority/permanent/etc. The execution
+  // is asynchronous. On completion, the action processor may be started
+  // depending on the |start_action_processor_| field. Note that every update
+  // attempt goes through this method.
+  void UpdateBootFlags();
+
+  // Called when the boot flags have been updated.
+  void CompleteUpdateBootFlags(bool success);
+
+  UpdateStatus status() const { return status_; }
+
+  int http_response_code() const { return http_response_code_; }
+  void set_http_response_code(int code) { http_response_code_ = code; }
+
+  void set_dbus_adaptor(UpdateEngineAdaptor* dbus_adaptor) {
+    dbus_adaptor_ = dbus_adaptor;
+  }
+
+  // This is the internal entry point for going through an
+  // update. If the current status is idle invokes Update.
+  // This is called by the DBus implementation.
+  virtual void CheckForUpdate(const std::string& app_version,
+                              const std::string& omaha_url,
+                              bool is_interactive);
+
+  // This is the internal entry point for going through a rollback. This will
+  // attempt to run the postinstall on the non-active partition and set it as
+  // the partition to boot from. If |powerwash| is True, perform a powerwash
+  // as part of rollback. Returns True on success.
+  bool Rollback(bool powerwash);
+
+  // This is the internal entry point for checking if we can rollback.
+  bool CanRollback() const;
+
+  // This is the internal entry point for getting a rollback partition name,
+  // if one exists. It returns the bootable rollback kernel device partition
+  // name or empty string if none is available.
+  BootControlInterface::Slot GetRollbackSlot() const;
+
+  // Initiates a reboot if the current state is
+  // UPDATED_NEED_REBOOT. Returns true on sucess, false otherwise.
+  bool RebootIfNeeded();
+
+  // DownloadActionDelegate methods:
+  void BytesReceived(uint64_t bytes_progressed,
+                     uint64_t bytes_received,
+                     uint64_t total) override;
+
+  // Returns that the update should be canceled when the download channel was
+  // changed.
+  bool ShouldCancel(ErrorCode* cancel_reason) override;
+
+  void DownloadComplete() override;
+
+  // Broadcasts the current status over D-Bus.
+  void BroadcastStatus();
+
+  // Returns the special flags to be added to ErrorCode values based on the
+  // parameters used in the current update attempt.
+  uint32_t GetErrorCodeFlags();
+
+  // Called at update_engine startup to do various house-keeping.
+  void UpdateEngineStarted();
+
+  // Reloads the device policy from libbrillo. Note: This method doesn't
+  // cause a real-time policy fetch from the policy server. It just reloads the
+  // latest value that libbrillo has cached. libbrillo fetches the policies
+  // from the server asynchronously at its own frequency.
+  virtual void RefreshDevicePolicy();
+
+  // Stores in |out_boot_time| the boottime (CLOCK_BOOTTIME) recorded at the
+  // time of the last successful update in the current boot. Returns false if
+  // there wasn't a successful update in the current boot.
+  virtual bool GetBootTimeAtUpdate(base::Time *out_boot_time);
+
+  // Returns a version OS version that was being used before the last reboot,
+  // and if that reboot happended to be into an update (current version).
+  // This will return an empty string otherwise.
+  std::string const& GetPrevVersion() const { return prev_version_; }
+
+  // Returns the number of consecutive failed update checks.
+  virtual unsigned int consecutive_failed_update_checks() const {
+    return consecutive_failed_update_checks_;
+  }
+
+  // Returns the poll interval dictated by Omaha, if provided; zero otherwise.
+  virtual unsigned int server_dictated_poll_interval() const {
+    return server_dictated_poll_interval_;
+  }
+
+  // Sets a callback to be used when either a forced update request is received
+  // (first argument set to true) or cleared by an update attempt (first
+  // argument set to false). The callback further encodes whether the forced
+  // check is an interactive one (second argument set to true). Takes ownership
+  // of the callback object. A null value disables callback on these events.
+  // Note that only one callback can be set, so effectively at most one client
+  // can be notified.
+  virtual void set_forced_update_pending_callback(
+      base::Callback<void(bool, bool)>*  // NOLINT(readability/function)
+      callback) {
+    forced_update_pending_callback_.reset(callback);
+  }
+
+  // Returns true if we should allow updates from any source. In official builds
+  // we want to restrict updates to known safe sources, but under certain
+  // conditions it's useful to allow updating from anywhere (e.g. to allow
+  // 'cros flash' to function properly).
+  virtual bool IsAnyUpdateSourceAllowed();
+
+ private:
+  // Update server URL for automated lab test.
+  static const char* const kTestUpdateUrl;
+
+  // Friend declarations for testing purposes.
+  friend class UpdateAttempterUnderTest;
+  friend class UpdateAttempterTest;
+  FRIEND_TEST(UpdateAttempterTest, ActionCompletedDownloadTest);
+  FRIEND_TEST(UpdateAttempterTest, ActionCompletedErrorTest);
+  FRIEND_TEST(UpdateAttempterTest, ActionCompletedOmahaRequestTest);
+  FRIEND_TEST(UpdateAttempterTest, CreatePendingErrorEventTest);
+  FRIEND_TEST(UpdateAttempterTest, CreatePendingErrorEventResumedTest);
+  FRIEND_TEST(UpdateAttempterTest, DisableDeltaUpdateIfNeededTest);
+  FRIEND_TEST(UpdateAttempterTest, MarkDeltaUpdateFailureTest);
+  FRIEND_TEST(UpdateAttempterTest, PingOmahaTest);
+  FRIEND_TEST(UpdateAttempterTest, ScheduleErrorEventActionNoEventTest);
+  FRIEND_TEST(UpdateAttempterTest, ScheduleErrorEventActionTest);
+  FRIEND_TEST(UpdateAttempterTest, UpdateTest);
+  FRIEND_TEST(UpdateAttempterTest, ReportDailyMetrics);
+  FRIEND_TEST(UpdateAttempterTest, BootTimeInUpdateMarkerFile);
+
+  // CertificateChecker::Observer method.
+  // Report metrics about the certificate being checked.
+  void CertificateChecked(ServerToCheck server_to_check,
+                          CertificateCheckResult result) override;
+
+  // Checks if it's more than 24 hours since daily metrics were last
+  // reported and, if so, reports daily metrics. Returns |true| if
+  // metrics were reported, |false| otherwise.
+  bool CheckAndReportDailyMetrics();
+
+  // Calculates and reports the age of the currently running OS. This
+  // is defined as the age of the /etc/lsb-release file.
+  void ReportOSAge();
+
+  // Sets the status to the given status and notifies a status update over dbus.
+  void SetStatusAndNotify(UpdateStatus status);
+
+  // Sets up the download parameters after receiving the update check response.
+  void SetupDownload();
+
+  // Creates an error event object in |error_event_| to be included in an
+  // OmahaRequestAction once the current action processor is done.
+  void CreatePendingErrorEvent(AbstractAction* action, ErrorCode code);
+
+  // If there's a pending error event allocated in |error_event_|, schedules an
+  // OmahaRequestAction with that event in the current processor, clears the
+  // pending event, updates the status and returns true. Returns false
+  // otherwise.
+  bool ScheduleErrorEventAction();
+
+  // Sets the cpu shares to |shares| and updates |shares_| if the new
+  // |shares| is different than the current |shares_|, otherwise simply
+  // returns.
+  void SetCpuShares(utils::CpuShares shares);
+
+  // Sets the cpu shares to low and sets up timeout events to increase it.
+  void SetupCpuSharesManagement();
+
+  // Resets the cpu shares to normal and destroys any scheduled timeout
+  // sources.
+  void CleanupCpuSharesManagement();
+
+  // The cpu shares timeout source callback sets the current cpu shares to
+  // normal.
+  void ManageCpuSharesCallback();
+
+  // Schedules an event loop callback to start the action processor. This is
+  // scheduled asynchronously to unblock the event loop.
+  void ScheduleProcessingStart();
+
+  // Checks if a full update is needed and forces it by updating the Omaha
+  // request params.
+  void DisableDeltaUpdateIfNeeded();
+
+  // If this was a delta update attempt that failed, count it so that a full
+  // update can be tried when needed.
+  void MarkDeltaUpdateFailure();
+
+  ProxyResolver* GetProxyResolver() {
+    return obeying_proxies_ ?
+        reinterpret_cast<ProxyResolver*>(&chrome_proxy_resolver_) :
+        reinterpret_cast<ProxyResolver*>(&direct_proxy_resolver_);
+  }
+
+  // Sends a ping to Omaha.
+  // This is used after an update has been applied and we're waiting for the
+  // user to reboot.  This ping helps keep the number of actives count
+  // accurate in case a user takes a long time to reboot the device after an
+  // update has been applied.
+  void PingOmaha();
+
+  // Helper method of Update() to calculate the update-related parameters
+  // from various sources and set the appropriate state. Please refer to
+  // Update() method for the meaning of the parametes.
+  bool CalculateUpdateParams(const std::string& app_version,
+                             const std::string& omaha_url,
+                             const std::string& target_channel,
+                             const std::string& target_version_prefix,
+                             bool obey_proxies,
+                             bool interactive);
+
+  // Calculates all the scattering related parameters (such as waiting period,
+  // which type of scattering is enabled, etc.) and also updates/deletes
+  // the corresponding prefs file used in scattering. Should be called
+  // only after the device policy has been loaded and set in the system_state_.
+  void CalculateScatteringParams(bool is_interactive);
+
+  // Sets a random value for the waiting period to wait for before downloading
+  // an update, if one available. This value will be upperbounded by the
+  // scatter factor value specified from policy.
+  void GenerateNewWaitingPeriod();
+
+  // Helper method of Update() and Rollback() to construct the sequence of
+  // actions to be performed for the postinstall.
+  // |previous_action| is the previous action to get
+  // bonded with the install_plan that gets passed to postinstall.
+  void BuildPostInstallActions(InstallPlanAction* previous_action);
+
+  // Helper method of Update() to construct the sequence of actions to
+  // be performed for an update check. Please refer to
+  // Update() method for the meaning of the parameters.
+  void BuildUpdateActions(bool interactive);
+
+  // Decrements the count in the kUpdateCheckCountFilePath.
+  // Returns True if successfully decremented, false otherwise.
+  bool DecrementUpdateCheckCount();
+
+  // Starts p2p and performs housekeeping. Returns true only if p2p is
+  // running and housekeeping was done.
+  bool StartP2PAndPerformHousekeeping();
+
+  // Calculates whether peer-to-peer should be used. Sets the
+  // |use_p2p_to_download_| and |use_p2p_to_share_| parameters
+  // on the |omaha_request_params_| object.
+  void CalculateP2PParams(bool interactive);
+
+  // Starts P2P if it's enabled and there are files to actually share.
+  // Called only at program startup. Returns true only if p2p was
+  // started and housekeeping was performed.
+  bool StartP2PAtStartup();
+
+  // Writes to the processing completed marker. Does nothing if
+  // |update_completed_marker_| is empty.
+  void WriteUpdateCompletedMarker();
+
+  // Sends a D-Bus message to the Chrome OS power manager asking it to reboot
+  // the system. Returns true on success.
+  bool RequestPowerManagerReboot();
+
+  // Reboots the system directly by calling /sbin/shutdown. Returns true on
+  // success.
+  bool RebootDirectly();
+
+  // Callback for the async UpdateCheckAllowed policy request. If |status| is
+  // |EvalStatus::kSucceeded|, either runs or suppresses periodic update checks,
+  // based on the content of |params|. Otherwise, retries the policy request.
+  void OnUpdateScheduled(
+      chromeos_update_manager::EvalStatus status,
+      const chromeos_update_manager::UpdateCheckParams& params);
+
+  // Updates the time an update was last attempted to the current time.
+  void UpdateLastCheckedTime();
+
+  // Returns whether an update is currently running or scheduled.
+  bool IsUpdateRunningOrScheduled();
+
+  // Last status notification timestamp used for throttling. Use monotonic
+  // TimeTicks to ensure that notifications are sent even if the system clock is
+  // set back in the middle of an update.
+  base::TimeTicks last_notify_time_;
+
+  std::vector<std::shared_ptr<AbstractAction>> actions_;
+  std::unique_ptr<ActionProcessor> processor_;
+
+  // External state of the system outside the update_engine process
+  // carved out separately to mock out easily in unit tests.
+  SystemState* system_state_;
+
+  // Pointer to the certificate checker instance to use.
+  CertificateChecker* cert_checker_;
+
+  // If non-null, this UpdateAttempter will send status updates over this
+  // dbus service.
+  UpdateEngineAdaptor* dbus_adaptor_ = nullptr;
+
+  // Pointer to the OmahaResponseHandlerAction in the actions_ vector.
+  std::shared_ptr<OmahaResponseHandlerAction> response_handler_action_;
+
+  // Pointer to the DownloadAction in the actions_ vector.
+  std::shared_ptr<DownloadAction> download_action_;
+
+  // Pointer to the preferences store interface. This is just a cached
+  // copy of system_state->prefs() because it's used in many methods and
+  // is convenient this way.
+  PrefsInterface* prefs_ = nullptr;
+
+  // Pending error event, if any.
+  std::unique_ptr<OmahaEvent> error_event_;
+
+  // If we should request a reboot even tho we failed the update
+  bool fake_update_success_ = false;
+
+  // HTTP server response code from the last HTTP request action.
+  int http_response_code_ = 0;
+
+  // Current cpu shares.
+  utils::CpuShares shares_ = utils::kCpuSharesNormal;
+
+  // The cpu shares management timeout task id.
+  brillo::MessageLoop::TaskId manage_shares_id_{
+      brillo::MessageLoop::kTaskIdNull};
+
+  // For status:
+  UpdateStatus status_{UpdateStatus::IDLE};
+  double download_progress_ = 0.0;
+  int64_t last_checked_time_ = 0;
+  std::string prev_version_;
+  std::string new_version_ = "0.0.0.0";
+  int64_t new_payload_size_ = 0;
+
+  // Common parameters for all Omaha requests.
+  OmahaRequestParams* omaha_request_params_ = nullptr;
+
+  // Number of consecutive manual update checks we've had where we obeyed
+  // Chrome's proxy settings.
+  int proxy_manual_checks_ = 0;
+
+  // If true, this update cycle we are obeying proxies
+  bool obeying_proxies_ = true;
+
+  // Our two proxy resolvers
+  DirectProxyResolver direct_proxy_resolver_;
+  ChromeBrowserProxyResolver chrome_proxy_resolver_;
+
+  // Originally, both of these flags are false. Once UpdateBootFlags is called,
+  // |update_boot_flags_running_| is set to true. As soon as UpdateBootFlags
+  // completes its asynchronous run, |update_boot_flags_running_| is reset to
+  // false and |updated_boot_flags_| is set to true. From that point on there
+  // will be no more changes to these flags.
+  //
+  // True if UpdateBootFlags has completed.
+  bool updated_boot_flags_ = false;
+  // True if UpdateBootFlags is running.
+  bool update_boot_flags_running_ = false;
+
+  // True if the action processor needs to be started by the boot flag updater.
+  bool start_action_processor_ = false;
+
+  // Used for fetching information about the device policy.
+  std::unique_ptr<policy::PolicyProvider> policy_provider_;
+
+  // The current scatter factor as found in the policy setting.
+  base::TimeDelta scatter_factor_;
+
+  // The number of consecutive failed update checks. Needed for calculating the
+  // next update check interval.
+  unsigned int consecutive_failed_update_checks_ = 0;
+
+  // The poll interval (in seconds) that was dictated by Omaha, if any; zero
+  // otherwise. This is needed for calculating the update check interval.
+  unsigned int server_dictated_poll_interval_ = 0;
+
+  // Tracks whether we have scheduled update checks.
+  bool waiting_for_scheduled_check_ = false;
+
+  // A callback to use when a forced update request is either received (true) or
+  // cleared by an update attempt (false). The second argument indicates whether
+  // this is an interactive update, and its value is significant iff the first
+  // argument is true.
+  std::unique_ptr<base::Callback<void(bool, bool)>>
+      forced_update_pending_callback_;
+
+  // The |app_version| and |omaha_url| parameters received during the latest
+  // forced update request. They are retrieved for use once the update is
+  // actually scheduled.
+  std::string forced_app_version_;
+  std::string forced_omaha_url_;
+
+  org::chromium::debugdProxyInterface* debugd_proxy_;
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateAttempter);
+};
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_UPDATE_ATTEMPTER_H_
diff --git a/update_attempter_unittest.cc b/update_attempter_unittest.cc
new file mode 100644
index 0000000..747a974
--- /dev/null
+++ b/update_attempter_unittest.cc
@@ -0,0 +1,1010 @@
+//
+// Copyright (C) 2012 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 "update_engine/update_attempter.h"
+
+#include <stdint.h>
+
+#include <memory>
+
+#include <base/files/file_util.h>
+#include <base/message_loop/message_loop.h>
+#include <brillo/bind_lambda.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/base_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <debugd/dbus-constants.h>
+#include <debugd/dbus-proxies.h>
+#include <debugd/dbus-proxy-mocks.h>
+#include <gtest/gtest.h>
+#include <policy/libpolicy.h>
+#include <policy/mock_device_policy.h>
+
+#include "libcros/dbus-proxies.h"
+#include "libcros/dbus-proxy-mocks.h"
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/common/mock_http_fetcher.h"
+#include "update_engine/common/mock_prefs.h"
+#include "update_engine/common/platform_constants.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/mock_action.h"
+#include "update_engine/mock_action_processor.h"
+#include "update_engine/mock_p2p_manager.h"
+#include "update_engine/mock_payload_state.h"
+#include "update_engine/payload_consumer/filesystem_verifier_action.h"
+#include "update_engine/payload_consumer/install_plan.h"
+#include "update_engine/payload_consumer/payload_constants.h"
+#include "update_engine/payload_consumer/postinstall_runner_action.h"
+
+using base::Time;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using org::chromium::LibCrosServiceInterfaceProxyMock;
+using org::chromium::UpdateEngineLibcrosProxyResolvedInterfaceProxyMock;
+using std::string;
+using std::unique_ptr;
+using testing::DoAll;
+using testing::InSequence;
+using testing::Ne;
+using testing::NiceMock;
+using testing::Property;
+using testing::Return;
+using testing::ReturnPointee;
+using testing::SaveArg;
+using testing::SetArgumentPointee;
+using testing::_;
+using update_engine::UpdateStatus;
+
+namespace chromeos_update_engine {
+
+// Test a subclass rather than the main class directly so that we can mock out
+// methods within the class. There're explicit unit tests for the mocked out
+// methods.
+class UpdateAttempterUnderTest : public UpdateAttempter {
+ public:
+  UpdateAttempterUnderTest(SystemState* system_state,
+                           LibCrosProxy* libcros_proxy,
+                           org::chromium::debugdProxyInterface* debugd_proxy)
+      : UpdateAttempter(system_state, nullptr, libcros_proxy, debugd_proxy) {}
+
+  // Wrap the update scheduling method, allowing us to opt out of scheduled
+  // updates for testing purposes.
+  void ScheduleUpdates() override {
+    schedule_updates_called_ = true;
+    if (do_schedule_updates_) {
+      UpdateAttempter::ScheduleUpdates();
+    } else {
+      LOG(INFO) << "[TEST] Update scheduling disabled.";
+    }
+  }
+  void EnableScheduleUpdates() { do_schedule_updates_ = true; }
+  void DisableScheduleUpdates() { do_schedule_updates_ = false; }
+
+  // Indicates whether ScheduleUpdates() was called.
+  bool schedule_updates_called() const { return schedule_updates_called_; }
+
+  // Need to expose forced_omaha_url_ so we can test it.
+  const string& forced_omaha_url() const { return forced_omaha_url_; }
+
+ private:
+  bool schedule_updates_called_ = false;
+  bool do_schedule_updates_ = true;
+};
+
+class UpdateAttempterTest : public ::testing::Test {
+ protected:
+  UpdateAttempterTest()
+      : service_interface_mock_(new LibCrosServiceInterfaceProxyMock()),
+        ue_proxy_resolved_interface_mock_(
+            new NiceMock<UpdateEngineLibcrosProxyResolvedInterfaceProxyMock>()),
+        libcros_proxy_(
+            brillo::make_unique_ptr(service_interface_mock_),
+            brillo::make_unique_ptr(ue_proxy_resolved_interface_mock_)),
+        certificate_checker_(fake_system_state_.mock_prefs(),
+                             &openssl_wrapper_) {
+    // Override system state members.
+    fake_system_state_.set_connection_manager(&mock_connection_manager);
+    fake_system_state_.set_update_attempter(&attempter_);
+    loop_.SetAsCurrent();
+
+    certificate_checker_.Init();
+
+    // Finish initializing the attempter.
+    attempter_.Init();
+  }
+
+  void SetUp() override {
+    CHECK(utils::MakeTempDirectory("UpdateAttempterTest-XXXXXX", &test_dir_));
+
+    EXPECT_EQ(nullptr, attempter_.dbus_adaptor_);
+    EXPECT_NE(nullptr, attempter_.system_state_);
+    EXPECT_EQ(0, attempter_.http_response_code_);
+    EXPECT_EQ(utils::kCpuSharesNormal, attempter_.shares_);
+    EXPECT_EQ(MessageLoop::kTaskIdNull, attempter_.manage_shares_id_);
+    EXPECT_EQ(UpdateStatus::IDLE, attempter_.status_);
+    EXPECT_EQ(0.0, attempter_.download_progress_);
+    EXPECT_EQ(0, attempter_.last_checked_time_);
+    EXPECT_EQ("0.0.0.0", attempter_.new_version_);
+    EXPECT_EQ(0, attempter_.new_payload_size_);
+    processor_ = new NiceMock<MockActionProcessor>();
+    attempter_.processor_.reset(processor_);  // Transfers ownership.
+    prefs_ = fake_system_state_.mock_prefs();
+
+    // Set up store/load semantics of P2P properties via the mock PayloadState.
+    actual_using_p2p_for_downloading_ = false;
+    EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+                SetUsingP2PForDownloading(_))
+        .WillRepeatedly(SaveArg<0>(&actual_using_p2p_for_downloading_));
+    EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+                GetUsingP2PForDownloading())
+        .WillRepeatedly(ReturnPointee(&actual_using_p2p_for_downloading_));
+    actual_using_p2p_for_sharing_ = false;
+    EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+                SetUsingP2PForSharing(_))
+        .WillRepeatedly(SaveArg<0>(&actual_using_p2p_for_sharing_));
+    EXPECT_CALL(*fake_system_state_.mock_payload_state(),
+                GetUsingP2PForDownloading())
+        .WillRepeatedly(ReturnPointee(&actual_using_p2p_for_sharing_));
+  }
+
+  void TearDown() override {
+    base::DeleteFile(base::FilePath(test_dir_), true);
+  }
+
+ public:
+  void ScheduleQuitMainLoop();
+
+  // Callbacks to run the different tests from the main loop.
+  void UpdateTestStart();
+  void UpdateTestVerify();
+  void RollbackTestStart(bool enterprise_rollback, bool valid_slot);
+  void RollbackTestVerify();
+  void PingOmahaTestStart();
+  void ReadScatterFactorFromPolicyTestStart();
+  void DecrementUpdateCheckCountTestStart();
+  void NoScatteringDoneDuringManualUpdateTestStart();
+  void P2PNotEnabledStart();
+  void P2PEnabledStart();
+  void P2PEnabledInteractiveStart();
+  void P2PEnabledStartingFailsStart();
+  void P2PEnabledHousekeepingFailsStart();
+
+  bool actual_using_p2p_for_downloading() {
+    return actual_using_p2p_for_downloading_;
+  }
+  bool actual_using_p2p_for_sharing() {
+    return actual_using_p2p_for_sharing_;
+  }
+
+  base::MessageLoopForIO base_loop_;
+  brillo::BaseMessageLoop loop_{&base_loop_};
+
+  FakeSystemState fake_system_state_;
+  org::chromium::debugdProxyMock debugd_proxy_mock_;
+  LibCrosServiceInterfaceProxyMock* service_interface_mock_;
+  UpdateEngineLibcrosProxyResolvedInterfaceProxyMock*
+      ue_proxy_resolved_interface_mock_;
+  LibCrosProxy libcros_proxy_;
+  OpenSSLWrapper openssl_wrapper_;
+  CertificateChecker certificate_checker_;
+  UpdateAttempterUnderTest attempter_{&fake_system_state_,
+                                      &libcros_proxy_,
+                                      &debugd_proxy_mock_};
+
+  NiceMock<MockActionProcessor>* processor_;
+  NiceMock<MockPrefs>* prefs_;  // Shortcut to fake_system_state_->mock_prefs().
+  NiceMock<MockConnectionManager> mock_connection_manager;
+
+  string test_dir_;
+
+  bool actual_using_p2p_for_downloading_;
+  bool actual_using_p2p_for_sharing_;
+};
+
+void UpdateAttempterTest::ScheduleQuitMainLoop() {
+  loop_.PostTask(FROM_HERE, base::Bind([this] { this->loop_.BreakLoop(); }));
+}
+
+TEST_F(UpdateAttempterTest, ActionCompletedDownloadTest) {
+  unique_ptr<MockHttpFetcher> fetcher(new MockHttpFetcher("", 0, nullptr));
+  fetcher->FailTransfer(503);  // Sets the HTTP response code.
+  DownloadAction action(prefs_, nullptr, fetcher.release());
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _)).Times(0);
+  attempter_.ActionCompleted(nullptr, &action, ErrorCode::kSuccess);
+  EXPECT_EQ(503, attempter_.http_response_code());
+  EXPECT_EQ(UpdateStatus::FINALIZING, attempter_.status());
+  ASSERT_EQ(nullptr, attempter_.error_event_.get());
+}
+
+TEST_F(UpdateAttempterTest, ActionCompletedErrorTest) {
+  MockAction action;
+  EXPECT_CALL(action, Type()).WillRepeatedly(Return("MockAction"));
+  attempter_.status_ = UpdateStatus::DOWNLOADING;
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _))
+      .WillOnce(Return(false));
+  attempter_.ActionCompleted(nullptr, &action, ErrorCode::kError);
+  ASSERT_NE(nullptr, attempter_.error_event_.get());
+}
+
+TEST_F(UpdateAttempterTest, ActionCompletedOmahaRequestTest) {
+  unique_ptr<MockHttpFetcher> fetcher(new MockHttpFetcher("", 0, nullptr));
+  fetcher->FailTransfer(500);  // Sets the HTTP response code.
+  OmahaRequestAction action(&fake_system_state_, nullptr,
+                            std::move(fetcher), false);
+  ObjectCollectorAction<OmahaResponse> collector_action;
+  BondActions(&action, &collector_action);
+  OmahaResponse response;
+  response.poll_interval = 234;
+  action.SetOutputObject(response);
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _)).Times(0);
+  attempter_.ActionCompleted(nullptr, &action, ErrorCode::kSuccess);
+  EXPECT_EQ(500, attempter_.http_response_code());
+  EXPECT_EQ(UpdateStatus::IDLE, attempter_.status());
+  EXPECT_EQ(234, attempter_.server_dictated_poll_interval_);
+  ASSERT_TRUE(attempter_.error_event_.get() == nullptr);
+}
+
+TEST_F(UpdateAttempterTest, ConstructWithUpdatedMarkerTest) {
+  FakePrefs fake_prefs;
+  string boot_id;
+  EXPECT_TRUE(utils::GetBootId(&boot_id));
+  fake_prefs.SetString(kPrefsUpdateCompletedOnBootId, boot_id);
+  fake_system_state_.set_prefs(&fake_prefs);
+  UpdateAttempterUnderTest attempter(&fake_system_state_, nullptr,
+                                     &debugd_proxy_mock_);
+  attempter.Init();
+  EXPECT_EQ(UpdateStatus::UPDATED_NEED_REBOOT, attempter.status());
+}
+
+TEST_F(UpdateAttempterTest, GetErrorCodeForActionTest) {
+  extern ErrorCode GetErrorCodeForAction(AbstractAction* action,
+                                              ErrorCode code);
+  EXPECT_EQ(ErrorCode::kSuccess,
+            GetErrorCodeForAction(nullptr, ErrorCode::kSuccess));
+
+  FakeSystemState fake_system_state;
+  OmahaRequestAction omaha_request_action(&fake_system_state, nullptr,
+                                          nullptr, false);
+  EXPECT_EQ(ErrorCode::kOmahaRequestError,
+            GetErrorCodeForAction(&omaha_request_action, ErrorCode::kError));
+  OmahaResponseHandlerAction omaha_response_handler_action(&fake_system_state_);
+  EXPECT_EQ(ErrorCode::kOmahaResponseHandlerError,
+            GetErrorCodeForAction(&omaha_response_handler_action,
+                                  ErrorCode::kError));
+  FilesystemVerifierAction filesystem_verifier_action(
+      fake_system_state_.boot_control(), VerifierMode::kVerifyTargetHash);
+  EXPECT_EQ(ErrorCode::kFilesystemVerifierError,
+            GetErrorCodeForAction(&filesystem_verifier_action,
+                                  ErrorCode::kError));
+  PostinstallRunnerAction postinstall_runner_action(
+      fake_system_state.fake_boot_control());
+  EXPECT_EQ(ErrorCode::kPostinstallRunnerError,
+            GetErrorCodeForAction(&postinstall_runner_action,
+                                  ErrorCode::kError));
+  MockAction action_mock;
+  EXPECT_CALL(action_mock, Type()).WillOnce(Return("MockAction"));
+  EXPECT_EQ(ErrorCode::kError,
+            GetErrorCodeForAction(&action_mock, ErrorCode::kError));
+}
+
+TEST_F(UpdateAttempterTest, DisableDeltaUpdateIfNeededTest) {
+  attempter_.omaha_request_params_->set_delta_okay(true);
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _))
+      .WillOnce(Return(false));
+  attempter_.DisableDeltaUpdateIfNeeded();
+  EXPECT_TRUE(attempter_.omaha_request_params_->delta_okay());
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(UpdateAttempter::kMaxDeltaUpdateFailures - 1),
+          Return(true)));
+  attempter_.DisableDeltaUpdateIfNeeded();
+  EXPECT_TRUE(attempter_.omaha_request_params_->delta_okay());
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(UpdateAttempter::kMaxDeltaUpdateFailures),
+          Return(true)));
+  attempter_.DisableDeltaUpdateIfNeeded();
+  EXPECT_FALSE(attempter_.omaha_request_params_->delta_okay());
+  EXPECT_CALL(*prefs_, GetInt64(_, _)).Times(0);
+  attempter_.DisableDeltaUpdateIfNeeded();
+  EXPECT_FALSE(attempter_.omaha_request_params_->delta_okay());
+}
+
+TEST_F(UpdateAttempterTest, MarkDeltaUpdateFailureTest) {
+  EXPECT_CALL(*prefs_, GetInt64(kPrefsDeltaUpdateFailures, _))
+      .WillOnce(Return(false))
+      .WillOnce(DoAll(SetArgumentPointee<1>(-1), Return(true)))
+      .WillOnce(DoAll(SetArgumentPointee<1>(1), Return(true)))
+      .WillOnce(DoAll(
+          SetArgumentPointee<1>(UpdateAttempter::kMaxDeltaUpdateFailures),
+          Return(true)));
+  EXPECT_CALL(*prefs_, SetInt64(Ne(kPrefsDeltaUpdateFailures), _))
+      .WillRepeatedly(Return(true));
+  EXPECT_CALL(*prefs_, SetInt64(kPrefsDeltaUpdateFailures, 1)).Times(2);
+  EXPECT_CALL(*prefs_, SetInt64(kPrefsDeltaUpdateFailures, 2));
+  EXPECT_CALL(*prefs_, SetInt64(kPrefsDeltaUpdateFailures,
+                               UpdateAttempter::kMaxDeltaUpdateFailures + 1));
+  for (int i = 0; i < 4; i ++)
+    attempter_.MarkDeltaUpdateFailure();
+}
+
+TEST_F(UpdateAttempterTest, ScheduleErrorEventActionNoEventTest) {
+  EXPECT_CALL(*processor_, EnqueueAction(_)).Times(0);
+  EXPECT_CALL(*processor_, StartProcessing()).Times(0);
+  EXPECT_CALL(*fake_system_state_.mock_payload_state(), UpdateFailed(_))
+      .Times(0);
+  OmahaResponse response;
+  string url1 = "http://url1";
+  response.payload_urls.push_back(url1);
+  response.payload_urls.push_back("https://url");
+  EXPECT_CALL(*(fake_system_state_.mock_payload_state()), GetCurrentUrl())
+      .WillRepeatedly(Return(url1));
+  fake_system_state_.mock_payload_state()->SetResponse(response);
+  attempter_.ScheduleErrorEventAction();
+  EXPECT_EQ(url1, fake_system_state_.mock_payload_state()->GetCurrentUrl());
+}
+
+TEST_F(UpdateAttempterTest, ScheduleErrorEventActionTest) {
+  EXPECT_CALL(*processor_,
+              EnqueueAction(Property(&AbstractAction::Type,
+                                     OmahaRequestAction::StaticType())));
+  EXPECT_CALL(*processor_, StartProcessing());
+  ErrorCode err = ErrorCode::kError;
+  EXPECT_CALL(*fake_system_state_.mock_payload_state(), UpdateFailed(err));
+  attempter_.error_event_.reset(new OmahaEvent(OmahaEvent::kTypeUpdateComplete,
+                                               OmahaEvent::kResultError,
+                                               err));
+  attempter_.ScheduleErrorEventAction();
+  EXPECT_EQ(UpdateStatus::REPORTING_ERROR_EVENT, attempter_.status());
+}
+
+namespace {
+// Actions that will be built as part of an update check.
+const string kUpdateActionTypes[] = {  // NOLINT(runtime/string)
+  OmahaRequestAction::StaticType(),
+  OmahaResponseHandlerAction::StaticType(),
+  FilesystemVerifierAction::StaticType(),
+  OmahaRequestAction::StaticType(),
+  DownloadAction::StaticType(),
+  OmahaRequestAction::StaticType(),
+  FilesystemVerifierAction::StaticType(),
+  PostinstallRunnerAction::StaticType(),
+  OmahaRequestAction::StaticType()
+};
+
+// Actions that will be built as part of a user-initiated rollback.
+const string kRollbackActionTypes[] = {  // NOLINT(runtime/string)
+  InstallPlanAction::StaticType(),
+  PostinstallRunnerAction::StaticType(),
+};
+
+}  // namespace
+
+void UpdateAttempterTest::UpdateTestStart() {
+  attempter_.set_http_response_code(200);
+
+  // Expect that the device policy is loaded by the UpdateAttempter at some
+  // point by calling RefreshDevicePolicy.
+  policy::MockDevicePolicy* device_policy = new policy::MockDevicePolicy();
+  attempter_.policy_provider_.reset(new policy::PolicyProvider(device_policy));
+  EXPECT_CALL(*device_policy, LoadPolicy())
+      .Times(testing::AtLeast(1)).WillRepeatedly(Return(true));
+
+  {
+    InSequence s;
+    for (size_t i = 0; i < arraysize(kUpdateActionTypes); ++i) {
+      EXPECT_CALL(*processor_,
+                  EnqueueAction(Property(&AbstractAction::Type,
+                                         kUpdateActionTypes[i])));
+    }
+    EXPECT_CALL(*processor_, StartProcessing());
+  }
+
+  attempter_.Update("", "", "", "", false, false);
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::UpdateTestVerify,
+                            base::Unretained(this)));
+}
+
+void UpdateAttempterTest::UpdateTestVerify() {
+  EXPECT_EQ(0, attempter_.http_response_code());
+  EXPECT_EQ(&attempter_, processor_->delegate());
+  EXPECT_EQ(arraysize(kUpdateActionTypes), attempter_.actions_.size());
+  for (size_t i = 0; i < arraysize(kUpdateActionTypes); ++i) {
+    EXPECT_EQ(kUpdateActionTypes[i], attempter_.actions_[i]->Type());
+  }
+  EXPECT_EQ(attempter_.response_handler_action_.get(),
+            attempter_.actions_[1].get());
+  DownloadAction* download_action =
+      dynamic_cast<DownloadAction*>(attempter_.actions_[4].get());
+  ASSERT_NE(nullptr, download_action);
+  EXPECT_EQ(&attempter_, download_action->delegate());
+  EXPECT_EQ(UpdateStatus::CHECKING_FOR_UPDATE, attempter_.status());
+  loop_.BreakLoop();
+}
+
+void UpdateAttempterTest::RollbackTestStart(
+    bool enterprise_rollback, bool valid_slot) {
+  // Create a device policy so that we can change settings.
+  policy::MockDevicePolicy* device_policy = new policy::MockDevicePolicy();
+  attempter_.policy_provider_.reset(new policy::PolicyProvider(device_policy));
+
+  EXPECT_CALL(*device_policy, LoadPolicy()).WillRepeatedly(Return(true));
+  fake_system_state_.set_device_policy(device_policy);
+
+  if (valid_slot) {
+    BootControlInterface::Slot rollback_slot = 1;
+    LOG(INFO) << "Test Mark Bootable: "
+              << BootControlInterface::SlotName(rollback_slot);
+    fake_system_state_.fake_boot_control()->SetSlotBootable(rollback_slot,
+                                                            true);
+  }
+
+  bool is_rollback_allowed = false;
+
+  // We only allow rollback on devices that are not enterprise enrolled and
+  // which have a valid slot to rollback to.
+  if (!enterprise_rollback && valid_slot) {
+     is_rollback_allowed = true;
+  }
+
+  if (enterprise_rollback) {
+    // We return an empty owner as this is an enterprise.
+    EXPECT_CALL(*device_policy, GetOwner(_)).WillRepeatedly(
+        DoAll(SetArgumentPointee<0>(string("")),
+        Return(true)));
+  } else {
+    // We return a fake owner as this is an owned consumer device.
+    EXPECT_CALL(*device_policy, GetOwner(_)).WillRepeatedly(
+        DoAll(SetArgumentPointee<0>(string("fake.mail@fake.com")),
+        Return(true)));
+  }
+
+  if (is_rollback_allowed) {
+    InSequence s;
+    for (size_t i = 0; i < arraysize(kRollbackActionTypes); ++i) {
+      EXPECT_CALL(*processor_,
+                  EnqueueAction(Property(&AbstractAction::Type,
+                                         kRollbackActionTypes[i])));
+    }
+    EXPECT_CALL(*processor_, StartProcessing());
+
+    EXPECT_TRUE(attempter_.Rollback(true));
+    loop_.PostTask(FROM_HERE,
+                   base::Bind(&UpdateAttempterTest::RollbackTestVerify,
+                              base::Unretained(this)));
+  } else {
+    EXPECT_FALSE(attempter_.Rollback(true));
+    loop_.BreakLoop();
+  }
+}
+
+void UpdateAttempterTest::RollbackTestVerify() {
+  // Verifies the actions that were enqueued.
+  EXPECT_EQ(&attempter_, processor_->delegate());
+  EXPECT_EQ(arraysize(kRollbackActionTypes), attempter_.actions_.size());
+  for (size_t i = 0; i < arraysize(kRollbackActionTypes); ++i) {
+    EXPECT_EQ(kRollbackActionTypes[i], attempter_.actions_[i]->Type());
+  }
+  EXPECT_EQ(UpdateStatus::ATTEMPTING_ROLLBACK, attempter_.status());
+  InstallPlanAction* install_plan_action =
+        dynamic_cast<InstallPlanAction*>(attempter_.actions_[0].get());
+  InstallPlan* install_plan = install_plan_action->install_plan();
+  EXPECT_EQ(0, install_plan->partitions.size());
+  EXPECT_EQ(install_plan->powerwash_required, true);
+  loop_.BreakLoop();
+}
+
+TEST_F(UpdateAttempterTest, UpdateTest) {
+  UpdateTestStart();
+  loop_.Run();
+}
+
+TEST_F(UpdateAttempterTest, RollbackTest) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::RollbackTestStart,
+                            base::Unretained(this),
+                            false, true));
+  loop_.Run();
+}
+
+TEST_F(UpdateAttempterTest, InvalidSlotRollbackTest) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::RollbackTestStart,
+                            base::Unretained(this),
+                            false, false));
+  loop_.Run();
+}
+
+TEST_F(UpdateAttempterTest, EnterpriseRollbackTest) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::RollbackTestStart,
+                            base::Unretained(this),
+                            true, true));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::PingOmahaTestStart() {
+  EXPECT_CALL(*processor_,
+              EnqueueAction(Property(&AbstractAction::Type,
+                                     OmahaRequestAction::StaticType())));
+  EXPECT_CALL(*processor_, StartProcessing());
+  attempter_.PingOmaha();
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, PingOmahaTest) {
+  EXPECT_FALSE(attempter_.waiting_for_scheduled_check_);
+  EXPECT_FALSE(attempter_.schedule_updates_called());
+  // Disable scheduling of subsequnet checks; we're using the DefaultPolicy in
+  // testing, which is more permissive than we want to handle here.
+  attempter_.DisableScheduleUpdates();
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::PingOmahaTestStart,
+                            base::Unretained(this)));
+  brillo::MessageLoopRunMaxIterations(&loop_, 100);
+  EXPECT_EQ(UpdateStatus::UPDATED_NEED_REBOOT, attempter_.status());
+  EXPECT_TRUE(attempter_.schedule_updates_called());
+}
+
+TEST_F(UpdateAttempterTest, CreatePendingErrorEventTest) {
+  MockAction action;
+  const ErrorCode kCode = ErrorCode::kDownloadTransferError;
+  attempter_.CreatePendingErrorEvent(&action, kCode);
+  ASSERT_NE(nullptr, attempter_.error_event_.get());
+  EXPECT_EQ(OmahaEvent::kTypeUpdateComplete, attempter_.error_event_->type);
+  EXPECT_EQ(OmahaEvent::kResultError, attempter_.error_event_->result);
+  EXPECT_EQ(
+      static_cast<ErrorCode>(static_cast<int>(kCode) |
+                             static_cast<int>(ErrorCode::kTestOmahaUrlFlag)),
+      attempter_.error_event_->error_code);
+}
+
+TEST_F(UpdateAttempterTest, CreatePendingErrorEventResumedTest) {
+  OmahaResponseHandlerAction *response_action =
+      new OmahaResponseHandlerAction(&fake_system_state_);
+  response_action->install_plan_.is_resume = true;
+  attempter_.response_handler_action_.reset(response_action);
+  MockAction action;
+  const ErrorCode kCode = ErrorCode::kInstallDeviceOpenError;
+  attempter_.CreatePendingErrorEvent(&action, kCode);
+  ASSERT_NE(nullptr, attempter_.error_event_.get());
+  EXPECT_EQ(OmahaEvent::kTypeUpdateComplete, attempter_.error_event_->type);
+  EXPECT_EQ(OmahaEvent::kResultError, attempter_.error_event_->result);
+  EXPECT_EQ(
+      static_cast<ErrorCode>(
+          static_cast<int>(kCode) |
+          static_cast<int>(ErrorCode::kResumedFlag) |
+          static_cast<int>(ErrorCode::kTestOmahaUrlFlag)),
+      attempter_.error_event_->error_code);
+}
+
+TEST_F(UpdateAttempterTest, P2PNotStartedAtStartupWhenNotEnabled) {
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(false);
+  EXPECT_CALL(mock_p2p_manager, EnsureP2PRunning()).Times(0);
+  attempter_.UpdateEngineStarted();
+}
+
+TEST_F(UpdateAttempterTest, P2PNotStartedAtStartupWhenEnabledButNotSharing) {
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  EXPECT_CALL(mock_p2p_manager, EnsureP2PRunning()).Times(0);
+  attempter_.UpdateEngineStarted();
+}
+
+TEST_F(UpdateAttempterTest, P2PStartedAtStartupWhenEnabledAndSharing) {
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  mock_p2p_manager.fake().SetCountSharedFilesResult(1);
+  EXPECT_CALL(mock_p2p_manager, EnsureP2PRunning());
+  attempter_.UpdateEngineStarted();
+}
+
+TEST_F(UpdateAttempterTest, P2PNotEnabled) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::P2PNotEnabledStart,
+                            base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::P2PNotEnabledStart() {
+  // If P2P is not enabled, check that we do not attempt housekeeping
+  // and do not convey that p2p is to be used.
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(false);
+  EXPECT_CALL(mock_p2p_manager, PerformHousekeeping()).Times(0);
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_FALSE(actual_using_p2p_for_downloading_);
+  EXPECT_FALSE(actual_using_p2p_for_sharing());
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, P2PEnabledStartingFails) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::P2PEnabledStartingFailsStart,
+                            base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::P2PEnabledStartingFailsStart() {
+  // If p2p is enabled, but starting it fails ensure we don't do
+  // any housekeeping and do not convey that p2p should be used.
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  mock_p2p_manager.fake().SetEnsureP2PRunningResult(false);
+  mock_p2p_manager.fake().SetPerformHousekeepingResult(false);
+  EXPECT_CALL(mock_p2p_manager, PerformHousekeeping()).Times(0);
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_FALSE(actual_using_p2p_for_downloading());
+  EXPECT_FALSE(actual_using_p2p_for_sharing());
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, P2PEnabledHousekeepingFails) {
+  loop_.PostTask(
+      FROM_HERE,
+      base::Bind(&UpdateAttempterTest::P2PEnabledHousekeepingFailsStart,
+                 base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::P2PEnabledHousekeepingFailsStart() {
+  // If p2p is enabled, starting it works but housekeeping fails, ensure
+  // we do not convey p2p is to be used.
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  mock_p2p_manager.fake().SetEnsureP2PRunningResult(true);
+  mock_p2p_manager.fake().SetPerformHousekeepingResult(false);
+  EXPECT_CALL(mock_p2p_manager, PerformHousekeeping());
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_FALSE(actual_using_p2p_for_downloading());
+  EXPECT_FALSE(actual_using_p2p_for_sharing());
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, P2PEnabled) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::P2PEnabledStart,
+                            base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::P2PEnabledStart() {
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  // If P2P is enabled and starting it works, check that we performed
+  // housekeeping and that we convey p2p should be used.
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  mock_p2p_manager.fake().SetEnsureP2PRunningResult(true);
+  mock_p2p_manager.fake().SetPerformHousekeepingResult(true);
+  EXPECT_CALL(mock_p2p_manager, PerformHousekeeping());
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_TRUE(actual_using_p2p_for_downloading());
+  EXPECT_TRUE(actual_using_p2p_for_sharing());
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, P2PEnabledInteractive) {
+  loop_.PostTask(FROM_HERE,
+                 base::Bind(&UpdateAttempterTest::P2PEnabledInteractiveStart,
+                            base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::P2PEnabledInteractiveStart() {
+  MockP2PManager mock_p2p_manager;
+  fake_system_state_.set_p2p_manager(&mock_p2p_manager);
+  // For an interactive check, if P2P is enabled and starting it
+  // works, check that we performed housekeeping and that we convey
+  // p2p should be used for sharing but NOT for downloading.
+  mock_p2p_manager.fake().SetP2PEnabled(true);
+  mock_p2p_manager.fake().SetEnsureP2PRunningResult(true);
+  mock_p2p_manager.fake().SetPerformHousekeepingResult(true);
+  EXPECT_CALL(mock_p2p_manager, PerformHousekeeping());
+  attempter_.Update("", "", "", "", false, true /* interactive */);
+  EXPECT_FALSE(actual_using_p2p_for_downloading());
+  EXPECT_TRUE(actual_using_p2p_for_sharing());
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, ReadScatterFactorFromPolicy) {
+  loop_.PostTask(
+      FROM_HERE,
+      base::Bind(&UpdateAttempterTest::ReadScatterFactorFromPolicyTestStart,
+                 base::Unretained(this)));
+  loop_.Run();
+}
+
+// Tests that the scatter_factor_in_seconds value is properly fetched
+// from the device policy.
+void UpdateAttempterTest::ReadScatterFactorFromPolicyTestStart() {
+  int64_t scatter_factor_in_seconds = 36000;
+
+  policy::MockDevicePolicy* device_policy = new policy::MockDevicePolicy();
+  attempter_.policy_provider_.reset(new policy::PolicyProvider(device_policy));
+
+  EXPECT_CALL(*device_policy, LoadPolicy()).WillRepeatedly(Return(true));
+  fake_system_state_.set_device_policy(device_policy);
+
+  EXPECT_CALL(*device_policy, GetScatterFactorInSeconds(_))
+      .WillRepeatedly(DoAll(
+          SetArgumentPointee<0>(scatter_factor_in_seconds),
+          Return(true)));
+
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_EQ(scatter_factor_in_seconds, attempter_.scatter_factor_.InSeconds());
+
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, DecrementUpdateCheckCountTest) {
+  loop_.PostTask(
+      FROM_HERE,
+      base::Bind(&UpdateAttempterTest::DecrementUpdateCheckCountTestStart,
+                 base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::DecrementUpdateCheckCountTestStart() {
+  // Tests that the scatter_factor_in_seconds value is properly fetched
+  // from the device policy and is decremented if value > 0.
+  int64_t initial_value = 5;
+  FakePrefs fake_prefs;
+  attempter_.prefs_ = &fake_prefs;
+
+  fake_system_state_.fake_hardware()->SetIsOOBEComplete(Time::UnixEpoch());
+
+  EXPECT_TRUE(fake_prefs.SetInt64(kPrefsUpdateCheckCount, initial_value));
+
+  int64_t scatter_factor_in_seconds = 10;
+
+  policy::MockDevicePolicy* device_policy = new policy::MockDevicePolicy();
+  attempter_.policy_provider_.reset(new policy::PolicyProvider(device_policy));
+
+  EXPECT_CALL(*device_policy, LoadPolicy()).WillRepeatedly(Return(true));
+  fake_system_state_.set_device_policy(device_policy);
+
+  EXPECT_CALL(*device_policy, GetScatterFactorInSeconds(_))
+      .WillRepeatedly(DoAll(
+          SetArgumentPointee<0>(scatter_factor_in_seconds),
+          Return(true)));
+
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_EQ(scatter_factor_in_seconds, attempter_.scatter_factor_.InSeconds());
+
+  // Make sure the file still exists.
+  EXPECT_TRUE(fake_prefs.Exists(kPrefsUpdateCheckCount));
+
+  int64_t new_value;
+  EXPECT_TRUE(fake_prefs.GetInt64(kPrefsUpdateCheckCount, &new_value));
+  EXPECT_EQ(initial_value - 1, new_value);
+
+  EXPECT_TRUE(
+      attempter_.omaha_request_params_->update_check_count_wait_enabled());
+
+  // However, if the count is already 0, it's not decremented. Test that.
+  initial_value = 0;
+  EXPECT_TRUE(fake_prefs.SetInt64(kPrefsUpdateCheckCount, initial_value));
+  attempter_.Update("", "", "", "", false, false);
+  EXPECT_TRUE(fake_prefs.Exists(kPrefsUpdateCheckCount));
+  EXPECT_TRUE(fake_prefs.GetInt64(kPrefsUpdateCheckCount, &new_value));
+  EXPECT_EQ(initial_value, new_value);
+
+  ScheduleQuitMainLoop();
+}
+
+TEST_F(UpdateAttempterTest, NoScatteringDoneDuringManualUpdateTestStart) {
+  loop_.PostTask(FROM_HERE, base::Bind(
+      &UpdateAttempterTest::NoScatteringDoneDuringManualUpdateTestStart,
+      base::Unretained(this)));
+  loop_.Run();
+}
+
+void UpdateAttempterTest::NoScatteringDoneDuringManualUpdateTestStart() {
+  // Tests that no scattering logic is enabled if the update check
+  // is manually done (as opposed to a scheduled update check)
+  int64_t initial_value = 8;
+  FakePrefs fake_prefs;
+  attempter_.prefs_ = &fake_prefs;
+
+  fake_system_state_.fake_hardware()->SetIsOOBEComplete(Time::UnixEpoch());
+  fake_system_state_.set_prefs(&fake_prefs);
+
+  EXPECT_TRUE(fake_prefs.SetInt64(kPrefsWallClockWaitPeriod, initial_value));
+  EXPECT_TRUE(fake_prefs.SetInt64(kPrefsUpdateCheckCount, initial_value));
+
+  // make sure scatter_factor is non-zero as scattering is disabled
+  // otherwise.
+  int64_t scatter_factor_in_seconds = 50;
+
+  policy::MockDevicePolicy* device_policy = new policy::MockDevicePolicy();
+  attempter_.policy_provider_.reset(new policy::PolicyProvider(device_policy));
+
+  EXPECT_CALL(*device_policy, LoadPolicy()).WillRepeatedly(Return(true));
+  fake_system_state_.set_device_policy(device_policy);
+
+  EXPECT_CALL(*device_policy, GetScatterFactorInSeconds(_))
+      .WillRepeatedly(DoAll(
+          SetArgumentPointee<0>(scatter_factor_in_seconds),
+          Return(true)));
+
+  // Trigger an interactive check so we can test that scattering is disabled.
+  attempter_.Update("", "", "", "", false, true);
+  EXPECT_EQ(scatter_factor_in_seconds, attempter_.scatter_factor_.InSeconds());
+
+  // Make sure scattering is disabled for manual (i.e. user initiated) update
+  // checks and all artifacts are removed.
+  EXPECT_FALSE(
+      attempter_.omaha_request_params_->wall_clock_based_wait_enabled());
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsWallClockWaitPeriod));
+  EXPECT_EQ(0, attempter_.omaha_request_params_->waiting_period().InSeconds());
+  EXPECT_FALSE(
+      attempter_.omaha_request_params_->update_check_count_wait_enabled());
+  EXPECT_FALSE(fake_prefs.Exists(kPrefsUpdateCheckCount));
+
+  ScheduleQuitMainLoop();
+}
+
+// Checks that we only report daily metrics at most every 24 hours.
+TEST_F(UpdateAttempterTest, ReportDailyMetrics) {
+  FakeClock fake_clock;
+  FakePrefs fake_prefs;
+
+  fake_system_state_.set_clock(&fake_clock);
+  fake_system_state_.set_prefs(&fake_prefs);
+
+  Time epoch = Time::FromInternalValue(0);
+  fake_clock.SetWallclockTime(epoch);
+
+  // If there is no kPrefsDailyMetricsLastReportedAt state variable,
+  // we should report.
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+  // We should not report again if no time has passed.
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // We should not report if only 10 hours has passed.
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(10));
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // We should not report if only 24 hours - 1 sec has passed.
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(24) -
+                              TimeDelta::FromSeconds(1));
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // We should report if 24 hours has passed.
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(24));
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+
+  // But then we should not report again..
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // .. until another 24 hours has passed
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(47));
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(48));
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // .. and another 24 hours
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(71));
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(72));
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // If the span between time of reporting and present time is
+  // negative, we report. This is in order to reset the timestamp and
+  // avoid an edge condition whereby a distant point in the future is
+  // in the state variable resulting in us never ever reporting again.
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(71));
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+
+  // In this case we should not update until the clock reads 71 + 24 = 95.
+  // Check that.
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(94));
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+  fake_clock.SetWallclockTime(epoch + TimeDelta::FromHours(95));
+  EXPECT_TRUE(attempter_.CheckAndReportDailyMetrics());
+  EXPECT_FALSE(attempter_.CheckAndReportDailyMetrics());
+}
+
+TEST_F(UpdateAttempterTest, BootTimeInUpdateMarkerFile) {
+  UpdateAttempterUnderTest attempter{&fake_system_state_,
+                                     nullptr,  // libcros_proxy
+                                     &debugd_proxy_mock_};
+  FakeClock fake_clock;
+  fake_clock.SetBootTime(Time::FromTimeT(42));
+  fake_system_state_.set_clock(&fake_clock);
+  FakePrefs fake_prefs;
+  fake_system_state_.set_prefs(&fake_prefs);
+  attempter.Init();
+
+  Time boot_time;
+  EXPECT_FALSE(attempter.GetBootTimeAtUpdate(&boot_time));
+
+  attempter.WriteUpdateCompletedMarker();
+
+  EXPECT_TRUE(attempter.GetBootTimeAtUpdate(&boot_time));
+  EXPECT_EQ(boot_time.ToTimeT(), 42);
+}
+
+TEST_F(UpdateAttempterTest, AnyUpdateSourceAllowedUnofficial) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(false);
+  EXPECT_TRUE(attempter_.IsAnyUpdateSourceAllowed());
+}
+
+TEST_F(UpdateAttempterTest, AnyUpdateSourceAllowedOfficialDevmode) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(false);
+  EXPECT_CALL(debugd_proxy_mock_, QueryDevFeatures(_, _, _))
+      .WillRepeatedly(DoAll(SetArgumentPointee<0>(0), Return(true)));
+  EXPECT_TRUE(attempter_.IsAnyUpdateSourceAllowed());
+}
+
+TEST_F(UpdateAttempterTest, AnyUpdateSourceDisallowedOfficialNormal) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(true);
+  // debugd should not be queried in this case.
+  EXPECT_CALL(debugd_proxy_mock_, QueryDevFeatures(_, _, _)).Times(0);
+  EXPECT_FALSE(attempter_.IsAnyUpdateSourceAllowed());
+}
+
+TEST_F(UpdateAttempterTest, AnyUpdateSourceDisallowedDebugdDisabled) {
+  using debugd::DEV_FEATURES_DISABLED;
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(false);
+  EXPECT_CALL(debugd_proxy_mock_, QueryDevFeatures(_, _, _))
+      .WillRepeatedly(
+          DoAll(SetArgumentPointee<0>(DEV_FEATURES_DISABLED), Return(true)));
+  EXPECT_FALSE(attempter_.IsAnyUpdateSourceAllowed());
+}
+
+TEST_F(UpdateAttempterTest, AnyUpdateSourceDisallowedDebugdFailure) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(false);
+  EXPECT_CALL(debugd_proxy_mock_, QueryDevFeatures(_, _, _))
+      .WillRepeatedly(Return(false));
+  EXPECT_FALSE(attempter_.IsAnyUpdateSourceAllowed());
+}
+
+TEST_F(UpdateAttempterTest, CheckForUpdateAUTest) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(true);
+  attempter_.CheckForUpdate("", "autest", true);
+  EXPECT_EQ(constants::kOmahaDefaultAUTestURL, attempter_.forced_omaha_url());
+}
+
+TEST_F(UpdateAttempterTest, CheckForUpdateScheduledAUTest) {
+  fake_system_state_.fake_hardware()->SetIsOfficialBuild(true);
+  fake_system_state_.fake_hardware()->SetIsNormalBootMode(true);
+  attempter_.CheckForUpdate("", "autest-scheduled", true);
+  EXPECT_EQ(constants::kOmahaDefaultAUTestURL, attempter_.forced_omaha_url());
+}
+
+}  // namespace chromeos_update_engine
diff --git a/update_engine-client.gyp b/update_engine-client.gyp
new file mode 100644
index 0000000..588fc63
--- /dev/null
+++ b/update_engine-client.gyp
@@ -0,0 +1,41 @@
+#
+# Copyright (C) 2015 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.
+#
+{
+  'targets': [
+    # update_engine client library generated headers. Used by other daemons and
+    # by the update_engine_client console program to interact with
+    # update_engine.
+    {
+      'target_name': 'libupdate_engine-client-headers',
+      'type': 'none',
+      'actions': [
+        {
+          'action_name': 'update_engine_client-dbus-proxies',
+          'variables': {
+            'dbus_service_config': 'dbus_bindings/dbus-service-config.json',
+            'proxy_output_file': 'include/update_engine/dbus-proxies.h',
+            'mock_output_file': 'include/update_engine/dbus-proxy-mocks.h',
+            'proxy_path_in_mocks': 'update_engine/dbus-proxies.h',
+          },
+          'sources': [
+            'dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml',
+          ],
+          'includes': ['../../../platform2/common-mk/generate-dbus-proxies.gypi'],
+        },
+      ],
+    },
+  ],
+}
diff --git a/update_engine.conf b/update_engine.conf
new file mode 100644
index 0000000..449e669
--- /dev/null
+++ b/update_engine.conf
@@ -0,0 +1,2 @@
+PAYLOAD_MAJOR_VERSION=2
+PAYLOAD_MINOR_VERSION=3
diff --git a/update_engine.gyp b/update_engine.gyp
new file mode 100644
index 0000000..2fa6ae8
--- /dev/null
+++ b/update_engine.gyp
@@ -0,0 +1,508 @@
+#
+# Copyright (C) 2015 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.
+#
+{
+  'target_defaults': {
+    'variables': {
+      'deps': [
+        'libbrillo-<(libbase_ver)',
+        'libchrome-<(libbase_ver)',
+      ],
+      # The -DUSE_* flags are passed from platform2.py. We use sane defaults
+      # here when these USE flags are not defined. You can set the default value
+      # for the USE flag in the ebuild.
+      'USE_dbus%': '1',
+      'USE_hwid_override%': '0',
+      'USE_mtd%': '0',
+      'USE_power_management%': '0',
+    },
+    'cflags': [
+      '-g',
+      '-ffunction-sections',
+      '-Wall',
+      '-Wextra',
+      '-Werror',
+      '-Wno-unused-parameter',
+    ],
+    'cflags_cc': [
+      '-fno-strict-aliasing',
+      '-Wnon-virtual-dtor',
+    ],
+    'ldflags': [
+      '-Wl,--gc-sections',
+    ],
+    'defines': [
+      '_FILE_OFFSET_BITS=64',
+      '_POSIX_C_SOURCE=199309L',
+      'USE_DBUS=<(USE_dbus)',
+      'USE_HWID_OVERRIDE=<(USE_hwid_override)',
+      'USE_MTD=<(USE_mtd)',
+      'USE_POWER_MANAGEMENT=<(USE_power_management)',
+    ],
+    'include_dirs': [
+      # We need this include dir because we include all the local code as
+      # "update_engine/...".
+      '<(platform2_root)/../aosp/system',
+      '<(platform2_root)/../aosp/system/update_engine/client_library/include',
+    ],
+  },
+  'targets': [
+    # Protobufs.
+    {
+      'target_name': 'update_metadata-protos',
+      'type': 'static_library',
+      'variables': {
+        'proto_in_dir': '.',
+        'proto_out_dir': 'include/update_engine',
+        'exported_deps': [
+          'protobuf-lite',
+        ],
+        'deps': ['<@(exported_deps)'],
+      },
+      'all_dependent_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+      },
+      'sources': [
+        'update_metadata.proto'
+      ],
+      'includes': ['../../../platform2/common-mk/protoc.gypi'],
+    },
+    # Chrome D-Bus bindings.
+    {
+      'target_name': 'update_engine-dbus-adaptor',
+      'type': 'none',
+      'variables': {
+        'dbus_adaptors_out_dir': 'include/dbus_bindings',
+        'dbus_xml_extension': 'dbus-xml',
+      },
+      'sources': [
+        'dbus_bindings/org.chromium.UpdateEngineInterface.dbus-xml',
+      ],
+      'includes': ['../../../platform2/common-mk/generate-dbus-adaptors.gypi'],
+    },
+    {
+      'target_name': 'update_engine-other-dbus-proxies',
+      'type': 'none',
+      'actions': [
+        {
+          'action_name': 'update_engine-dbus-libcros-client',
+          'variables': {
+            'mock_output_file': 'include/libcros/dbus-proxy-mocks.h',
+            'proxy_output_file': 'include/libcros/dbus-proxies.h'
+          },
+          'sources': [
+            'dbus_bindings/org.chromium.LibCrosService.dbus-xml',
+          ],
+          'includes': ['../../../platform2/common-mk/generate-dbus-proxies.gypi'],
+        },
+      ],
+    },
+    # The payload application component and common dependencies.
+    {
+      'target_name': 'libpayload_consumer',
+      'type': 'static_library',
+      'dependencies': [
+        'update_metadata-protos',
+      ],
+      #TODO(deymo): Remove unused dependencies once we stop including files
+      # from the root directory.
+      'variables': {
+        'exported_deps': [
+          'libcrypto',
+          'libcurl',
+          'libssl',
+          'xz-embedded',
+        ],
+        'deps': ['<@(exported_deps)'],
+      },
+      'all_dependent_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+      },
+      'link_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+        'libraries': [
+          '-lbz2',
+          '-lrt',
+        ],
+      },
+      'sources': [
+        'common/action_processor.cc',
+        'common/boot_control_stub.cc',
+        'common/certificate_checker.cc',
+        'common/clock.cc',
+        'common/constants.cc',
+        'common/hash_calculator.cc',
+        'common/http_common.cc',
+        'common/http_fetcher.cc',
+        'common/hwid_override.cc',
+        'common/libcurl_http_fetcher.cc',
+        'common/multi_range_http_fetcher.cc',
+        'common/platform_constants_chromeos.cc',
+        'common/prefs.cc',
+        'common/subprocess.cc',
+        'common/terminator.cc',
+        'common/utils.cc',
+        'payload_consumer/bzip_extent_writer.cc',
+        'payload_consumer/delta_performer.cc',
+        'payload_consumer/download_action.cc',
+        'payload_consumer/extent_writer.cc',
+        'payload_consumer/file_descriptor.cc',
+        'payload_consumer/file_writer.cc',
+        'payload_consumer/filesystem_verifier_action.cc',
+        'payload_consumer/install_plan.cc',
+        'payload_consumer/payload_constants.cc',
+        'payload_consumer/payload_verifier.cc',
+        'payload_consumer/postinstall_runner_action.cc',
+        'payload_consumer/xz_extent_writer.cc',
+      ],
+      'conditions': [
+        ['USE_mtd == 1', {
+          'sources': [
+            'payload_consumer/mtd_file_descriptor.cc',
+          ],
+          'link_settings': {
+            'libraries': [
+              '-lmtdutils',
+            ],
+          },
+        }],
+      ],
+    },
+    # The main daemon static_library with all the code used to check for updates
+    # with Omaha and expose a DBus daemon.
+    {
+      'target_name': 'libupdate_engine',
+      'type': 'static_library',
+      'dependencies': [
+        'libpayload_consumer',
+        'update_metadata-protos',
+        'update_engine-dbus-adaptor',
+        'update_engine-other-dbus-proxies',
+      ],
+      'variables': {
+        'exported_deps': [
+          'dbus-1',
+          'libdebugd-client',
+          'libsession_manager-client',
+          'libmetrics-<(libbase_ver)',
+          'libpower_manager-client',
+          'libupdate_engine-client',
+          'libshill-client',
+          'expat',
+        ],
+        'deps': ['<@(exported_deps)'],
+      },
+      'all_dependent_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+      },
+      'link_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+        'libraries': [
+          '-lbz2',
+          '-lpolicy-<(libbase_ver)',
+          '-lrootdev',
+          '-lrt',
+          '-lvboot_host',
+        ],
+      },
+      'sources': [
+        'boot_control_chromeos.cc',
+        'chrome_browser_proxy_resolver.cc',
+        'connection_manager.cc',
+        'daemon.cc',
+        'dbus_service.cc',
+        'hardware_chromeos.cc',
+        'image_properties_chromeos.cc',
+        'libcros_proxy.cc',
+        'metrics.cc',
+        'metrics_utils.cc',
+        'omaha_request_action.cc',
+        'omaha_request_params.cc',
+        'omaha_response_handler_action.cc',
+        'p2p_manager.cc',
+        'payload_state.cc',
+        'proxy_resolver.cc',
+        'real_system_state.cc',
+        'shill_proxy.cc',
+        'update_attempter.cc',
+        'update_manager/boxed_value.cc',
+        'update_manager/chromeos_policy.cc',
+        'update_manager/default_policy.cc',
+        'update_manager/evaluation_context.cc',
+        'update_manager/policy.cc',
+        'update_manager/real_config_provider.cc',
+        'update_manager/real_device_policy_provider.cc',
+        'update_manager/real_random_provider.cc',
+        'update_manager/real_shill_provider.cc',
+        'update_manager/real_system_provider.cc',
+        'update_manager/real_time_provider.cc',
+        'update_manager/real_updater_provider.cc',
+        'update_manager/state_factory.cc',
+        'update_manager/update_manager.cc',
+        'update_status_utils.cc',
+      ],
+    },
+    # update_engine daemon.
+    {
+      'target_name': 'update_engine',
+      'type': 'executable',
+      'dependencies': [
+        'libupdate_engine',
+      ],
+      'sources': [
+        'main.cc',
+      ],
+    },
+    # update_engine console client.
+    {
+      'target_name': 'update_engine_client',
+      'type': 'executable',
+      'variables': {
+        'exported_deps': [
+          'libupdate_engine-client',
+        ],
+        'deps': ['<@(exported_deps)'],
+      },
+      'sources': [
+        'update_engine_client.cc',
+      ],
+    },
+    # server-side code. This is used for delta_generator and unittests but not
+    # for any client code.
+    {
+      'target_name': 'libpayload_generator',
+      'type': 'static_library',
+      'dependencies': [
+        'libpayload_consumer',
+        'update_metadata-protos',
+      ],
+      'variables': {
+        'exported_deps': [
+          'ext2fs',
+        ],
+        'deps': ['<@(exported_deps)'],
+      },
+      'all_dependent_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+      },
+      'link_settings': {
+        'variables': {
+          'deps': [
+            '<@(exported_deps)',
+          ],
+        },
+      },
+      'sources': [
+        'payload_generator/ab_generator.cc',
+        'payload_generator/annotated_operation.cc',
+        'payload_generator/blob_file_writer.cc',
+        'payload_generator/block_mapping.cc',
+        'payload_generator/bzip.cc',
+        'payload_generator/cycle_breaker.cc',
+        'payload_generator/delta_diff_generator.cc',
+        'payload_generator/delta_diff_utils.cc',
+        'payload_generator/ext2_filesystem.cc',
+        'payload_generator/extent_ranges.cc',
+        'payload_generator/extent_utils.cc',
+        'payload_generator/full_update_generator.cc',
+        'payload_generator/graph_types.cc',
+        'payload_generator/graph_utils.cc',
+        'payload_generator/inplace_generator.cc',
+        'payload_generator/payload_file.cc',
+        'payload_generator/payload_generation_config.cc',
+        'payload_generator/payload_signer.cc',
+        'payload_generator/raw_filesystem.cc',
+        'payload_generator/tarjan.cc',
+        'payload_generator/topological_sort.cc',
+      ],
+    },
+    # server-side delta generator.
+    {
+      'target_name': 'delta_generator',
+      'type': 'executable',
+      'dependencies': [
+        'libpayload_consumer',
+        'libpayload_generator',
+      ],
+      'link_settings': {
+        'ldflags!': [
+          '-pie',
+        ],
+      },
+      'sources': [
+        'payload_generator/generate_delta_main.cc',
+      ],
+    },
+  ],
+  'conditions': [
+    ['USE_test == 1', {
+      'targets': [
+        # Public keys used for unit testing.
+        {
+          'target_name': 'update_engine-testkeys',
+          'type': 'none',
+          'variables': {
+            'openssl_pem_in_dir': '.',
+            'openssl_pem_out_dir': 'include/update_engine',
+          },
+          'sources': [
+            'unittest_key.pem',
+            'unittest_key2.pem',
+          ],
+          'includes': ['../../../platform2/common-mk/openssl_pem.gypi'],
+        },
+        # Unpacks sample images used for testing.
+        {
+          'target_name': 'update_engine-test_images',
+          'type': 'none',
+          'variables': {
+            'image_out_dir': '.',
+          },
+          'sources': [
+            'sample_images/sample_images.tar.bz2',
+          ],
+          'includes': ['tar_bunzip2.gypi'],
+        },
+        # Test HTTP Server.
+        {
+          'target_name': 'test_http_server',
+          'type': 'executable',
+          'dependencies': ['libupdate_engine'],
+          'sources': [
+            'test_http_server.cc',
+          ],
+        },
+        # Main unittest file.
+        {
+          'target_name': 'update_engine_unittests',
+          'type': 'executable',
+          'includes': ['../../../platform2/common-mk/common_test.gypi'],
+          'variables': {
+            'deps': [
+              'libbrillo-test-<(libbase_ver)',
+              'libchrome-test-<(libbase_ver)',
+              'libdebugd-client-test',
+              'libpower_manager-client-test',
+              'libsession_manager-client-test',
+              'libshill-client-test',
+            ],
+          },
+          'dependencies': [
+            'libupdate_engine',
+            'libpayload_generator',
+          ],
+          'includes': ['../../../platform2/common-mk/common_test.gypi'],
+          'sources': [
+            'chrome_browser_proxy_resolver_unittest.cc',
+            'common/action_pipe_unittest.cc',
+            'common/action_processor_unittest.cc',
+            'common/action_unittest.cc',
+            'common/boot_control_chromeos_unittest.cc',
+            'common/certificate_checker_unittest.cc',
+            'common/fake_prefs.cc',
+            'common/hash_calculator_unittest.cc',
+            'common/http_fetcher_unittest.cc',
+            'common/hwid_override_unittest.cc',
+            'common/mock_http_fetcher.cc',
+            'common/prefs_unittest.cc',
+            'common/subprocess_unittest.cc',
+            'common/terminator_unittest.cc',
+            'common/test_utils.cc',
+            'common/utils_unittest.cc',
+            'connection_manager_unittest.cc',
+            'dbus_service_unittest.cc',
+            'fake_shill_proxy.cc',
+            'fake_system_state.cc',
+            'metrics_utils_unittest.cc',
+            'omaha_request_action_unittest.cc',
+            'omaha_request_params_unittest.cc',
+            'omaha_response_handler_action_unittest.cc',
+            'p2p_manager_unittest.cc',
+            'payload_consumer/bzip_extent_writer_unittest.cc',
+            'payload_consumer/delta_performer_integration_test.cc',
+            'payload_consumer/delta_performer_unittest.cc',
+            'payload_consumer/download_action_unittest.cc',
+            'payload_consumer/extent_writer_unittest.cc',
+            'payload_consumer/file_writer_unittest.cc',
+            'payload_consumer/filesystem_verifier_action_unittest.cc',
+            'payload_consumer/postinstall_runner_action_unittest.cc',
+            'payload_consumer/xz_extent_writer_unittest.cc',
+            'payload_generator/ab_generator_unittest.cc',
+            'payload_generator/blob_file_writer_unittest.cc',
+            'payload_generator/block_mapping_unittest.cc',
+            'payload_generator/cycle_breaker_unittest.cc',
+            'payload_generator/delta_diff_utils_unittest.cc',
+            'payload_generator/ext2_filesystem_unittest.cc',
+            'payload_generator/extent_ranges_unittest.cc',
+            'payload_generator/extent_utils_unittest.cc',
+            'payload_generator/fake_filesystem.cc',
+            'payload_generator/full_update_generator_unittest.cc',
+            'payload_generator/graph_utils_unittest.cc',
+            'payload_generator/inplace_generator_unittest.cc',
+            'payload_generator/payload_file_unittest.cc',
+            'payload_generator/payload_generation_config_unittest.cc',
+            'payload_generator/payload_signer_unittest.cc',
+            'payload_generator/tarjan_unittest.cc',
+            'payload_generator/topological_sort_unittest.cc',
+            'payload_generator/zip_unittest.cc',
+            'payload_state_unittest.cc',
+            'update_attempter_unittest.cc',
+            'update_manager/boxed_value_unittest.cc',
+            'update_manager/chromeos_policy_unittest.cc',
+            'update_manager/evaluation_context_unittest.cc',
+            'update_manager/generic_variables_unittest.cc',
+            'update_manager/prng_unittest.cc',
+            'update_manager/real_config_provider_unittest.cc',
+            'update_manager/real_device_policy_provider_unittest.cc',
+            'update_manager/real_random_provider_unittest.cc',
+            'update_manager/real_shill_provider_unittest.cc',
+            'update_manager/real_system_provider_unittest.cc',
+            'update_manager/real_time_provider_unittest.cc',
+            'update_manager/real_updater_provider_unittest.cc',
+            'update_manager/umtest_utils.cc',
+            'update_manager/update_manager_unittest.cc',
+            'update_manager/variable_unittest.cc',
+            # Main entry point for runnning tests.
+            'testrunner.cc',
+          ],
+        },
+      ],
+    }],
+  ],
+}
diff --git a/update_engine.rc b/update_engine.rc
new file mode 100644
index 0000000..69fc7af
--- /dev/null
+++ b/update_engine.rc
@@ -0,0 +1,4 @@
+service update_engine /system/bin/update_engine --logtostderr --foreground
+    class late_start
+    user root
+    group root system dbus inet
diff --git a/update_engine_client.cc b/update_engine_client.cc
new file mode 100644
index 0000000..b59f22f
--- /dev/null
+++ b/update_engine_client.cc
@@ -0,0 +1,653 @@
+//
+// Copyright (C) 2012 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 <inttypes.h>
+#include <sysexits.h>
+#include <unistd.h>
+
+#include <string>
+
+#include <base/bind.h>
+#include <base/command_line.h>
+#include <base/logging.h>
+#include <base/macros.h>
+#include <brillo/daemons/dbus_daemon.h>
+#include <brillo/flag_helper.h>
+#include <dbus/bus.h>
+#include <update_engine/dbus-constants.h>
+#include <update_engine/dbus-proxies.h>
+
+using std::string;
+using update_engine::kAttemptUpdateFlagNonInteractive;
+using update_engine::kUpdateEngineServiceName;
+
+namespace {
+
+// Constant to signal that we need to continue running the daemon after
+// initialization.
+const int kContinueRunning = -1;
+
+class UpdateEngineClient : public brillo::DBusDaemon {
+ public:
+  UpdateEngineClient(int argc, char** argv) : argc_(argc), argv_(argv) {}
+  ~UpdateEngineClient() override = default;
+
+ protected:
+  int OnInit() override {
+    int ret = DBusDaemon::OnInit();
+    if (ret != EX_OK)
+      return ret;
+    if (!InitProxy())
+      return 1;
+    // Wait for the UpdateEngine to be available or timeout.
+    proxy_->GetObjectProxy()->WaitForServiceToBeAvailable(
+        base::Bind(&UpdateEngineClient::OnServiceAvailable,
+                   base::Unretained(this)));
+    base::MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&UpdateEngineClient::OnServiceAvailableTimeout,
+                   base::Unretained(this)),
+        base::TimeDelta::FromSeconds(10));
+    return EX_OK;
+  }
+
+ private:
+  bool InitProxy();
+
+  // Callback called when the UpdateEngine service becomes available.
+  void OnServiceAvailable(bool service_is_available);
+
+  // Callback called when the UpdateEngine service doesn't become available
+  // after a timeout.
+  void OnServiceAvailableTimeout();
+
+
+  // Callback called when a StatusUpdate signal is received.
+  void OnStatusUpdateSignal(int64_t last_checked_time,
+                            double progress,
+                            const string& current_operation,
+                            const string& new_version,
+                            int64_t new_size);
+  // Callback called when the OnStatusUpdateSignal() handler is registered.
+  void OnStatusUpdateSignalRegistration(const string& interface,
+                                        const string& signal_name,
+                                        bool success);
+
+  // Registers a callback that prints on stderr the received StatusUpdate
+  // signals.
+  // The daemon should continue running for this to work.
+  void WatchForUpdates();
+
+  void ResetStatus();
+
+  // Show the status of the update engine in stdout.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  void ShowStatus();
+
+  // Return the current operation status, such as UPDATE_STATUS_IDLE.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  string GetCurrentOperation();
+
+  void Rollback(bool rollback);
+  string GetRollbackPartition();
+  void CheckForUpdates(const string& app_version,
+                       const string& omaha_url,
+                       bool interactive);
+
+  // Reboot the device if a reboot is needed.
+  // Blocking call. Ignores failures.
+  void RebootIfNeeded();
+
+  // Getter and setter for the target channel. If |get_current_channel| is true,
+  // the current channel instead of the target channel will be returned.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  void SetTargetChannel(const string& target_channel, bool allow_powerwash);
+  string GetChannel(bool get_current_channel);
+
+  // Getter and setter for the updates over cellular connections.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  void SetUpdateOverCellularPermission(bool allowed);
+  bool GetUpdateOverCellularPermission();
+
+  // Getter and setter for the updates from P2P permission.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  void SetP2PUpdatePermission(bool enabled);
+  bool GetP2PUpdatePermission();
+
+  // This is similar to watching for updates but rather than registering
+  // a signal watch, actively poll the daemon just in case it stops
+  // sending notifications.
+  void WaitForUpdateComplete();
+  void OnUpdateCompleteCheck(int64_t last_checked_time,
+                             double progress,
+                             const string& current_operation,
+                             const string& new_version,
+                             int64_t new_size);
+
+  // Blocking call. Exits the program with error 1 in case of an error.
+  void ShowPrevVersion();
+
+  // Returns whether the current status is such that a reboot is needed.
+  // Blocking call. Exits the program with error 1 in case of an error.
+  bool GetIsRebootNeeded();
+
+  // Blocks until a reboot is needed. If the reboot is needed, exits the program
+  // with 0. Otherwise it exits the program with 1 if an error occurs before
+  // the reboot is needed.
+  void WaitForRebootNeeded();
+  void OnRebootNeededCheck(int64_t last_checked_time,
+                           double progress,
+                           const string& current_operation,
+                           const string& new_version,
+                           int64_t new_size);
+  // Callback called when the OnRebootNeededCheck() handler is registered. This
+  // is useful to check at this point if the reboot is needed, without loosing
+  // any StatusUpdate signals and avoiding the race condition.
+  void OnRebootNeededCheckRegistration(const string& interface,
+                                       const string& signal_name,
+                                       bool success);
+
+  // Main method that parses and triggers all the actions based on the passed
+  // flags.
+  int ProcessFlags();
+
+  // DBus Proxy to the update_engine daemon object used for all the calls.
+  std::unique_ptr<org::chromium::UpdateEngineInterfaceProxy> proxy_;
+
+  // Copy of argc and argv passed to main().
+  int argc_;
+  char** argv_;
+
+  // Tell whether the UpdateEngine service is available after startup.
+  bool service_is_available_{false};
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateEngineClient);
+};
+
+bool UpdateEngineClient::InitProxy() {
+  proxy_.reset(new org::chromium::UpdateEngineInterfaceProxy(bus_));
+
+  if (!proxy_->GetObjectProxy()) {
+    LOG(ERROR) << "Error getting dbus proxy for " << kUpdateEngineServiceName;
+    return false;
+  }
+  return true;
+}
+
+void UpdateEngineClient::OnServiceAvailable(bool service_is_available) {
+  service_is_available_ = service_is_available;
+  if (!service_is_available) {
+    LOG(ERROR) << "UpdateEngineService not available.";
+    QuitWithExitCode(-1);
+  }
+  int ret = ProcessFlags();
+  if (ret != kContinueRunning)
+    QuitWithExitCode(ret);
+}
+
+void UpdateEngineClient::OnServiceAvailableTimeout() {
+  if (!service_is_available_) {
+    LOG(ERROR) << "Waiting for UpdateEngineService timeout. Is update_engine "
+                  "daemon running?";
+    QuitWithExitCode(-1);
+  }
+}
+
+void UpdateEngineClient::OnStatusUpdateSignal(
+    int64_t last_checked_time,
+    double progress,
+    const string& current_operation,
+    const string& new_version,
+    int64_t new_size) {
+  LOG(INFO) << "Got status update:";
+  LOG(INFO) << "  last_checked_time: " << last_checked_time;
+  LOG(INFO) << "  progress: " << progress;
+  LOG(INFO) << "  current_operation: " << current_operation;
+  LOG(INFO) << "  new_version: " << new_version;
+  LOG(INFO) << "  new_size: " << new_size;
+}
+
+void UpdateEngineClient::OnStatusUpdateSignalRegistration(
+    const string& interface,
+    const string& signal_name,
+    bool success) {
+  VLOG(1) << "OnStatusUpdateSignalRegistration(" << interface << ", "
+          << signal_name << ", " << success << ");";
+  if (!success) {
+    LOG(ERROR) << "Couldn't connect to the " << signal_name << " signal.";
+    exit(1);
+  }
+}
+
+void UpdateEngineClient::WatchForUpdates() {
+  proxy_->RegisterStatusUpdateSignalHandler(
+      base::Bind(&UpdateEngineClient::OnStatusUpdateSignal,
+                 base::Unretained(this)),
+      base::Bind(&UpdateEngineClient::OnStatusUpdateSignalRegistration,
+                 base::Unretained(this)));
+}
+
+void UpdateEngineClient::ResetStatus() {
+  bool ret = proxy_->ResetStatus(nullptr);
+  CHECK(ret) << "ResetStatus() failed.";
+}
+
+void UpdateEngineClient::ShowStatus() {
+  int64_t last_checked_time = 0;
+  double progress = 0.0;
+  string current_op;
+  string new_version;
+  int64_t new_size = 0;
+
+  bool ret = proxy_->GetStatus(
+      &last_checked_time, &progress, &current_op, &new_version, &new_size,
+      nullptr);
+  CHECK(ret) << "GetStatus() failed";
+  printf("LAST_CHECKED_TIME=%" PRIi64 "\nPROGRESS=%f\nCURRENT_OP=%s\n"
+         "NEW_VERSION=%s\nNEW_SIZE=%" PRIi64 "\n",
+         last_checked_time,
+         progress,
+         current_op.c_str(),
+         new_version.c_str(),
+         new_size);
+}
+
+string UpdateEngineClient::GetCurrentOperation() {
+  int64_t last_checked_time = 0;
+  double progress = 0.0;
+  string current_op;
+  string new_version;
+  int64_t new_size = 0;
+
+  bool ret = proxy_->GetStatus(
+      &last_checked_time, &progress, &current_op, &new_version, &new_size,
+      nullptr);
+  CHECK(ret) << "GetStatus() failed";
+  return current_op;
+}
+
+void UpdateEngineClient::Rollback(bool rollback) {
+  bool ret = proxy_->AttemptRollback(rollback, nullptr);
+  CHECK(ret) << "Rollback request failed.";
+}
+
+string UpdateEngineClient::GetRollbackPartition() {
+  string rollback_partition;
+  bool ret = proxy_->GetRollbackPartition(&rollback_partition, nullptr);
+  CHECK(ret) << "Error while querying rollback partition availabilty.";
+  return rollback_partition;
+}
+
+void UpdateEngineClient::CheckForUpdates(const string& app_version,
+                                         const string& omaha_url,
+                                         bool interactive) {
+  int32_t flags = interactive ? 0 : kAttemptUpdateFlagNonInteractive;
+  bool ret = proxy_->AttemptUpdateWithFlags(app_version, omaha_url, flags,
+                                            nullptr);
+  CHECK(ret) << "Error checking for update.";
+}
+
+void UpdateEngineClient::RebootIfNeeded() {
+  bool ret = proxy_->RebootIfNeeded(nullptr);
+  if (!ret) {
+    // Reboot error code doesn't necessarily mean that a reboot
+    // failed. For example, D-Bus may be shutdown before we receive the
+    // result.
+    LOG(INFO) << "RebootIfNeeded() failure ignored.";
+  }
+}
+
+void UpdateEngineClient::SetTargetChannel(const string& target_channel,
+                                          bool allow_powerwash) {
+  bool ret = proxy_->SetChannel(target_channel, allow_powerwash, nullptr);
+  CHECK(ret) << "Error setting the channel.";
+  LOG(INFO) << "Channel permanently set to: " << target_channel;
+}
+
+string UpdateEngineClient::GetChannel(bool get_current_channel) {
+  string channel;
+  bool ret = proxy_->GetChannel(get_current_channel, &channel, nullptr);
+  CHECK(ret) << "Error getting the channel.";
+  return channel;
+}
+
+void UpdateEngineClient::SetUpdateOverCellularPermission(bool allowed) {
+  bool ret = proxy_->SetUpdateOverCellularPermission(allowed, nullptr);
+  CHECK(ret) << "Error setting the update over cellular setting.";
+}
+
+bool UpdateEngineClient::GetUpdateOverCellularPermission() {
+  bool allowed;
+  bool ret = proxy_->GetUpdateOverCellularPermission(&allowed, nullptr);
+  CHECK(ret) << "Error getting the update over cellular setting.";
+  return allowed;
+}
+
+void UpdateEngineClient::SetP2PUpdatePermission(bool enabled) {
+  bool ret = proxy_->SetP2PUpdatePermission(enabled, nullptr);
+  CHECK(ret) << "Error setting the peer-to-peer update setting.";
+}
+
+bool UpdateEngineClient::GetP2PUpdatePermission() {
+  bool enabled;
+  bool ret = proxy_->GetP2PUpdatePermission(&enabled, nullptr);
+  CHECK(ret) << "Error getting the peer-to-peer update setting.";
+  return enabled;
+}
+
+void UpdateEngineClient::OnUpdateCompleteCheck(
+    int64_t /* last_checked_time */,
+    double /* progress */,
+    const string& current_operation,
+    const string& /* new_version */,
+    int64_t /* new_size */) {
+  if (current_operation == update_engine::kUpdateStatusIdle) {
+    LOG(ERROR) << "Update failed, current operations is " << current_operation;
+    exit(1);
+  }
+  if (current_operation == update_engine::kUpdateStatusUpdatedNeedReboot) {
+    LOG(INFO) << "Update succeeded -- reboot needed.";
+    exit(0);
+  }
+}
+
+void UpdateEngineClient::WaitForUpdateComplete() {
+  proxy_->RegisterStatusUpdateSignalHandler(
+      base::Bind(&UpdateEngineClient::OnUpdateCompleteCheck,
+                 base::Unretained(this)),
+      base::Bind(&UpdateEngineClient::OnStatusUpdateSignalRegistration,
+                 base::Unretained(this)));
+}
+
+void UpdateEngineClient::ShowPrevVersion() {
+  string prev_version = nullptr;
+
+  bool ret = proxy_->GetPrevVersion(&prev_version, nullptr);;
+  if (!ret) {
+    LOG(ERROR) << "Error getting previous version.";
+  } else {
+    LOG(INFO) << "Previous version = " << prev_version;
+  }
+}
+
+bool UpdateEngineClient::GetIsRebootNeeded() {
+  return GetCurrentOperation() == update_engine::kUpdateStatusUpdatedNeedReboot;
+}
+
+void UpdateEngineClient::OnRebootNeededCheck(
+    int64_t /* last_checked_time */,
+    double /* progress */,
+    const string& current_operation,
+    const string& /* new_version */,
+    int64_t /* new_size */) {
+  if (current_operation == update_engine::kUpdateStatusUpdatedNeedReboot) {
+    LOG(INFO) << "Reboot needed.";
+    exit(0);
+  }
+}
+
+void UpdateEngineClient::OnRebootNeededCheckRegistration(
+    const string& interface,
+    const string& signal_name,
+    bool success) {
+  if (GetIsRebootNeeded())
+    exit(0);
+  if (!success) {
+    LOG(ERROR) << "Couldn't connect to the " << signal_name << " signal.";
+    exit(1);
+  }
+}
+
+// Blocks until a reboot is needed. Returns true if waiting succeeded,
+// false if an error occurred.
+void UpdateEngineClient::WaitForRebootNeeded() {
+  proxy_->RegisterStatusUpdateSignalHandler(
+      base::Bind(&UpdateEngineClient::OnUpdateCompleteCheck,
+                 base::Unretained(this)),
+      base::Bind(&UpdateEngineClient::OnStatusUpdateSignalRegistration,
+                 base::Unretained(this)));
+  if (GetIsRebootNeeded())
+    exit(0);
+}
+
+int UpdateEngineClient::ProcessFlags() {
+  DEFINE_string(app_version, "", "Force the current app version.");
+  DEFINE_string(channel, "",
+                "Set the target channel. The device will be powerwashed if the "
+                "target channel is more stable than the current channel unless "
+                "--nopowerwash is specified.");
+  DEFINE_bool(check_for_update, false, "Initiate check for updates.");
+  DEFINE_bool(follow, false, "Wait for any update operations to complete."
+              "Exit status is 0 if the update succeeded, and 1 otherwise.");
+  DEFINE_bool(interactive, true, "Mark the update request as interactive.");
+  DEFINE_string(omaha_url, "", "The URL of the Omaha update server.");
+  DEFINE_string(p2p_update, "",
+                "Enables (\"yes\") or disables (\"no\") the peer-to-peer update"
+                " sharing.");
+  DEFINE_bool(powerwash, true, "When performing rollback or channel change, "
+              "do a powerwash or allow it respectively.");
+  DEFINE_bool(reboot, false, "Initiate a reboot if needed.");
+  DEFINE_bool(is_reboot_needed, false, "Exit status 0 if reboot is needed, "
+              "2 if reboot is not needed or 1 if an error occurred.");
+  DEFINE_bool(block_until_reboot_is_needed, false, "Blocks until reboot is "
+              "needed. Returns non-zero exit status if an error occurred.");
+  DEFINE_bool(reset_status, false, "Sets the status in update_engine to idle.");
+  DEFINE_bool(rollback, false,
+              "Perform a rollback to the previous partition. The device will "
+              "be powerwashed unless --nopowerwash is specified.");
+  DEFINE_bool(can_rollback, false, "Shows whether rollback partition "
+              "is available.");
+  DEFINE_bool(show_channel, false, "Show the current and target channels.");
+  DEFINE_bool(show_p2p_update, false,
+              "Show the current setting for peer-to-peer update sharing.");
+  DEFINE_bool(show_update_over_cellular, false,
+              "Show the current setting for updates over cellular networks.");
+  DEFINE_bool(status, false, "Print the status to stdout.");
+  DEFINE_bool(update, false, "Forces an update and waits for it to complete. "
+              "Implies --follow.");
+  DEFINE_string(update_over_cellular, "",
+                "Enables (\"yes\") or disables (\"no\") the updates over "
+                "cellular networks.");
+  DEFINE_bool(watch_for_updates, false,
+              "Listen for status updates and print them to the screen.");
+  DEFINE_bool(prev_version, false,
+              "Show the previous OS version used before the update reboot.");
+
+  // Boilerplate init commands.
+  base::CommandLine::Init(argc_, argv_);
+  brillo::FlagHelper::Init(argc_, argv_, "Chromium OS Update Engine Client");
+
+  // Ensure there are no positional arguments.
+  const std::vector<string> positional_args =
+      base::CommandLine::ForCurrentProcess()->GetArgs();
+  if (!positional_args.empty()) {
+    LOG(ERROR) << "Found a positional argument '" << positional_args.front()
+               << "'. If you want to pass a value to a flag, pass it as "
+                  "--flag=value.";
+    return 1;
+  }
+
+  // Update the status if requested.
+  if (FLAGS_reset_status) {
+    LOG(INFO) << "Setting Update Engine status to idle ...";
+    ResetStatus();
+    LOG(INFO) << "ResetStatus succeeded; to undo partition table changes run:\n"
+                 "(D=$(rootdev -d) P=$(rootdev -s); cgpt p -i$(($(echo ${P#$D} "
+                 "| sed 's/^[^0-9]*//')-1)) $D;)";
+  }
+
+  // Changes the current update over cellular network setting.
+  if (!FLAGS_update_over_cellular.empty()) {
+    bool allowed = FLAGS_update_over_cellular == "yes";
+    if (!allowed && FLAGS_update_over_cellular != "no") {
+      LOG(ERROR) << "Unknown option: \"" << FLAGS_update_over_cellular
+                 << "\". Please specify \"yes\" or \"no\".";
+    } else {
+      SetUpdateOverCellularPermission(allowed);
+    }
+  }
+
+  // Show the current update over cellular network setting.
+  if (FLAGS_show_update_over_cellular) {
+    bool allowed = GetUpdateOverCellularPermission();
+    LOG(INFO) << "Current update over cellular network setting: "
+              << (allowed ? "ENABLED" : "DISABLED");
+  }
+
+  if (!FLAGS_powerwash && !FLAGS_rollback && FLAGS_channel.empty()) {
+    LOG(ERROR) << "powerwash flag only makes sense rollback or channel change";
+    return 1;
+  }
+
+  // Change the P2P enabled setting.
+  if (!FLAGS_p2p_update.empty()) {
+    bool enabled = FLAGS_p2p_update == "yes";
+    if (!enabled && FLAGS_p2p_update != "no") {
+      LOG(ERROR) << "Unknown option: \"" << FLAGS_p2p_update
+                 << "\". Please specify \"yes\" or \"no\".";
+    } else {
+      SetP2PUpdatePermission(enabled);
+    }
+  }
+
+  // Show the rollback availability.
+  if (FLAGS_can_rollback) {
+    string rollback_partition = GetRollbackPartition();
+    bool can_rollback = true;
+    if (rollback_partition.empty()) {
+      rollback_partition = "UNAVAILABLE";
+      can_rollback = false;
+    } else {
+      rollback_partition = "AVAILABLE: " + rollback_partition;
+    }
+
+    LOG(INFO) << "Rollback partition: " << rollback_partition;
+    if (!can_rollback) {
+      return 1;
+    }
+  }
+
+  // Show the current P2P enabled setting.
+  if (FLAGS_show_p2p_update) {
+    bool enabled = GetP2PUpdatePermission();
+    LOG(INFO) << "Current update using P2P setting: "
+              << (enabled ? "ENABLED" : "DISABLED");
+  }
+
+  // First, update the target channel if requested.
+  if (!FLAGS_channel.empty())
+    SetTargetChannel(FLAGS_channel, FLAGS_powerwash);
+
+  // Show the current and target channels if requested.
+  if (FLAGS_show_channel) {
+    string current_channel = GetChannel(true);
+    LOG(INFO) << "Current Channel: " << current_channel;
+
+    string target_channel = GetChannel(false);
+    if (!target_channel.empty())
+      LOG(INFO) << "Target Channel (pending update): " << target_channel;
+  }
+
+  bool do_update_request = FLAGS_check_for_update | FLAGS_update |
+      !FLAGS_app_version.empty() | !FLAGS_omaha_url.empty();
+  if (FLAGS_update)
+    FLAGS_follow = true;
+
+  if (do_update_request && FLAGS_rollback) {
+    LOG(ERROR) << "Incompatible flags specified with rollback."
+               << "Rollback should not include update-related flags.";
+    return 1;
+  }
+
+  if (FLAGS_rollback) {
+    LOG(INFO) << "Requesting rollback.";
+    Rollback(FLAGS_powerwash);
+  }
+
+  // Initiate an update check, if necessary.
+  if (do_update_request) {
+    LOG_IF(WARNING, FLAGS_reboot) << "-reboot flag ignored.";
+    string app_version = FLAGS_app_version;
+    if (FLAGS_update && app_version.empty()) {
+      app_version = "ForcedUpdate";
+      LOG(INFO) << "Forcing an update by setting app_version to ForcedUpdate.";
+    }
+    LOG(INFO) << "Initiating update check and install.";
+    CheckForUpdates(app_version, FLAGS_omaha_url, FLAGS_interactive);
+  }
+
+  // These final options are all mutually exclusive with one another.
+  if (FLAGS_follow + FLAGS_watch_for_updates + FLAGS_reboot +
+      FLAGS_status + FLAGS_is_reboot_needed +
+      FLAGS_block_until_reboot_is_needed > 1) {
+    LOG(ERROR) << "Multiple exclusive options selected. "
+               << "Select only one of --follow, --watch_for_updates, --reboot, "
+               << "--is_reboot_needed, --block_until_reboot_is_needed, "
+               << "or --status.";
+    return 1;
+  }
+
+  if (FLAGS_status) {
+    LOG(INFO) << "Querying Update Engine status...";
+    ShowStatus();
+    return 0;
+  }
+
+  if (FLAGS_follow) {
+    LOG(INFO) << "Waiting for update to complete.";
+    WaitForUpdateComplete();
+    return kContinueRunning;
+  }
+
+  if (FLAGS_watch_for_updates) {
+    LOG(INFO) << "Watching for status updates.";
+    WatchForUpdates();
+    return kContinueRunning;
+  }
+
+  if (FLAGS_reboot) {
+    LOG(INFO) << "Requesting a reboot...";
+    RebootIfNeeded();
+    return 0;
+  }
+
+  if (FLAGS_prev_version) {
+    ShowPrevVersion();
+  }
+
+  if (FLAGS_is_reboot_needed) {
+    // In case of error GetIsRebootNeeded() will exit with 1.
+    if (GetIsRebootNeeded()) {
+      return 0;
+    } else {
+      return 2;
+    }
+  }
+
+  if (FLAGS_block_until_reboot_is_needed) {
+    WaitForRebootNeeded();
+    return kContinueRunning;
+  }
+
+  return 0;
+}
+
+}  // namespace
+
+int main(int argc, char** argv) {
+  UpdateEngineClient client(argc, argv);
+  return client.Run();
+}
diff --git a/update_manager/boxed_value.cc b/update_manager/boxed_value.cc
new file mode 100644
index 0000000..a4aeede
--- /dev/null
+++ b/update_manager/boxed_value.cc
@@ -0,0 +1,194 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/boxed_value.h"
+
+#include <stdint.h>
+
+#include <set>
+#include <string>
+
+#include <base/strings/string_number_conversions.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/shill_provider.h"
+#include "update_engine/update_manager/updater_provider.h"
+
+using std::set;
+using std::string;
+
+namespace chromeos_update_manager {
+
+// Template instantiation for common types; used in BoxedValue::ToString().
+// Keep in sync with boxed_value_unitttest.cc.
+
+template<>
+string BoxedValue::ValuePrinter<string>(const void* value) {
+  const string* val = reinterpret_cast<const string*>(value);
+  return *val;
+}
+
+template<>
+string BoxedValue::ValuePrinter<int>(const void* value) {
+  const int* val = reinterpret_cast<const int*>(value);
+  return base::IntToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<unsigned int>(const void* value) {
+  const unsigned int* val = reinterpret_cast<const unsigned int*>(value);
+  return base::UintToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<int64_t>(const void* value) {
+  const int64_t* val = reinterpret_cast<const int64_t*>(value);
+  return base::Int64ToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<uint64_t>(const void* value) {
+  const uint64_t* val =
+    reinterpret_cast<const uint64_t*>(value);
+  return base::Uint64ToString(static_cast<uint64_t>(*val));
+}
+
+template<>
+string BoxedValue::ValuePrinter<bool>(const void* value) {
+  const bool* val = reinterpret_cast<const bool*>(value);
+  return *val ? "true" : "false";
+}
+
+template<>
+string BoxedValue::ValuePrinter<double>(const void* value) {
+  const double* val = reinterpret_cast<const double*>(value);
+  return base::DoubleToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<base::Time>(const void* value) {
+  const base::Time* val = reinterpret_cast<const base::Time*>(value);
+  return chromeos_update_engine::utils::ToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<base::TimeDelta>(const void* value) {
+  const base::TimeDelta* val = reinterpret_cast<const base::TimeDelta*>(value);
+  return chromeos_update_engine::utils::FormatTimeDelta(*val);
+}
+
+static string ConnectionTypeToString(ConnectionType type) {
+  switch (type) {
+    case ConnectionType::kEthernet:
+      return "Ethernet";
+    case ConnectionType::kWifi:
+      return "Wifi";
+    case ConnectionType::kWimax:
+      return "Wimax";
+    case ConnectionType::kBluetooth:
+      return "Bluetooth";
+    case ConnectionType::kCellular:
+      return "Cellular";
+    case ConnectionType::kUnknown:
+      return "Unknown";
+  }
+  NOTREACHED();
+  return "Unknown";
+}
+
+template<>
+string BoxedValue::ValuePrinter<ConnectionType>(const void* value) {
+  const ConnectionType* val = reinterpret_cast<const ConnectionType*>(value);
+  return ConnectionTypeToString(*val);
+}
+
+template<>
+string BoxedValue::ValuePrinter<set<ConnectionType>>(const void* value) {
+  string ret = "";
+  const set<ConnectionType>* val =
+      reinterpret_cast<const set<ConnectionType>*>(value);
+  for (auto& it : *val) {
+    ConnectionType type = it;
+    if (ret.size() > 0)
+      ret += ",";
+    ret += ConnectionTypeToString(type);
+  }
+  return ret;
+}
+
+template<>
+string BoxedValue::ValuePrinter<ConnectionTethering>(const void* value) {
+  const ConnectionTethering* val =
+      reinterpret_cast<const ConnectionTethering*>(value);
+  switch (*val) {
+    case ConnectionTethering::kNotDetected:
+      return "Not Detected";
+    case ConnectionTethering::kSuspected:
+      return "Suspected";
+    case ConnectionTethering::kConfirmed:
+      return "Confirmed";
+    case ConnectionTethering::kUnknown:
+      return "Unknown";
+  }
+  NOTREACHED();
+  return "Unknown";
+}
+
+template<>
+string BoxedValue::ValuePrinter<Stage>(const void* value) {
+  const Stage* val = reinterpret_cast<const Stage*>(value);
+  switch (*val) {
+    case Stage::kIdle:
+      return "Idle";
+    case Stage::kCheckingForUpdate:
+      return "Checking For Update";
+    case Stage::kUpdateAvailable:
+      return "Update Available";
+    case Stage::kDownloading:
+      return "Downloading";
+    case Stage::kVerifying:
+      return "Verifying";
+    case Stage::kFinalizing:
+      return "Finalizing";
+    case Stage::kUpdatedNeedReboot:
+      return "Updated, Need Reboot";
+    case Stage::kReportingErrorEvent:
+      return "Reporting Error Event";
+    case Stage::kAttemptingRollback:
+      return "Attempting Rollback";
+  }
+  NOTREACHED();
+  return "Unknown";
+}
+
+template<>
+string BoxedValue::ValuePrinter<UpdateRequestStatus>(const void* value) {
+  const UpdateRequestStatus* val =
+      reinterpret_cast<const UpdateRequestStatus*>(value);
+  switch (*val) {
+    case UpdateRequestStatus::kNone:
+      return "None";
+    case UpdateRequestStatus::kInteractive:
+      return "Interactive";
+    case UpdateRequestStatus::kPeriodic:
+      return "Periodic";
+  }
+  NOTREACHED();
+  return "Unknown";
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/boxed_value.h b/update_manager/boxed_value.h
new file mode 100644
index 0000000..5f41835
--- /dev/null
+++ b/update_manager/boxed_value.h
@@ -0,0 +1,124 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_BOXED_VALUE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_BOXED_VALUE_H_
+
+#include <memory>
+#include <string>
+
+#include <base/macros.h>
+
+namespace chromeos_update_manager {
+
+// BoxedValue is a class to hold pointers of a given type that deletes them when
+// the instance goes out of scope, as std::unique_ptr<T> does. The main
+// difference with it is that the type T is not part of the class, i.e., this
+// isn't a parametric class. The class has a parametric constructor that accepts
+// a const T* which will define the type of the object passed on delete.
+//
+// It is safe to use this class in linked containers such as std::list and
+// std::map but the object can't be copied. This means that you need to
+// construct the BoxedValue in place using a container method like emplace()
+// or move it with std::move().
+//
+//   list<BoxedValue> lst;
+//   lst.emplace_back(new const int(42));
+//   lst.emplace_back(new const string("Hello world!"));
+//
+//   map<int, BoxedValue> m;
+//   m.emplace(123, std::move(BoxedValue(new const string("Hola mundo!"))));
+//
+//   auto it = m.find(42);
+//   if (it != m.end())
+//     cout << "m[42] points to " << it->second.value() << endl;
+//   cout << "m[33] points to " << m[33].value() << endl;
+//
+// Since copy and assign are not allowed, you can't create a copy of the
+// BoxedValue which means that you can only use a reference to it.
+//
+
+class BoxedValue {
+ public:
+  // Creates an empty BoxedValue. Since the pointer can't be assigned from other
+  // BoxedValues or pointers, this is only useful in places where a default
+  // constructor is required, such as std::map::operator[].
+  BoxedValue() : value_(nullptr), deleter_(nullptr), printer_(nullptr) {}
+
+  // Creates a BoxedValue for the passed pointer |value|. The BoxedValue keeps
+  // the ownership of this pointer and can't be released.
+  template<typename T>
+  explicit BoxedValue(const T* value)
+    : value_(static_cast<const void*>(value)), deleter_(ValueDeleter<T>),
+      printer_(ValuePrinter<T>) {}
+
+  // The move constructor takes ownership of the pointer since the semantics of
+  // it allows to render the passed BoxedValue undefined. You need to use the
+  // move constructor explicitly preventing it from accidental references,
+  // like in:
+  //   BoxedValue new_box(std::move(other_box));
+  BoxedValue(BoxedValue&& other)  // NOLINT(build/c++11)
+      : value_(other.value_), deleter_(other.deleter_),
+        printer_(other.printer_) {
+    other.value_ = nullptr;
+    other.deleter_ = nullptr;
+    other.printer_ = nullptr;
+  }
+
+  // Deletes the |value| passed on construction using the delete for the passed
+  // type.
+  ~BoxedValue() {
+    if (deleter_)
+      deleter_(value_);
+  }
+
+  const void* value() const { return value_; }
+
+  std::string ToString() const {
+    if (!printer_)
+      return "(no printer)";
+    if (!value_)
+      return "(no value)";
+    return printer_(value_);
+  }
+
+  // Static method to call the destructor of the right type.
+  template<typename T>
+  static void ValueDeleter(const void* value) {
+    delete reinterpret_cast<const T*>(value);
+  }
+
+  // Static method to print a type. See boxed_value.cc for common
+  // instantiations.
+  template<typename T>
+  static std::string ValuePrinter(const void* value);
+
+ private:
+  // A pointer to the cached value.
+  const void* value_;
+
+  // A function that calls delete for the right type of value_.
+  void (*deleter_)(const void*);
+
+  // A function that converts value_ to a string.
+  std::string (*printer_)(const void*);
+
+  DISALLOW_COPY_AND_ASSIGN(BoxedValue);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_BOXED_VALUE_H_
diff --git a/update_manager/boxed_value_unittest.cc b/update_manager/boxed_value_unittest.cc
new file mode 100644
index 0000000..47bfd8f
--- /dev/null
+++ b/update_manager/boxed_value_unittest.cc
@@ -0,0 +1,232 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/boxed_value.h"
+
+#include <gtest/gtest.h>
+#include <list>
+#include <map>
+#include <set>
+#include <string>
+
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+
+#include "update_engine/update_manager/shill_provider.h"
+#include "update_engine/update_manager/umtest_utils.h"
+#include "update_engine/update_manager/updater_provider.h"
+
+using base::Time;
+using base::TimeDelta;
+using std::list;
+using std::map;
+using std::set;
+using std::string;
+
+namespace chromeos_update_manager {
+
+// The DeleterMarker flags a bool variable when the class is destroyed.
+class DeleterMarker {
+ public:
+  explicit DeleterMarker(bool* marker) : marker_(marker) { *marker_ = false; }
+
+  ~DeleterMarker() { *marker_ = true; }
+
+ private:
+  friend string BoxedValue::ValuePrinter<DeleterMarker>(const void *);
+
+  // Pointer to the bool marker.
+  bool* marker_;
+};
+
+template<>
+string BoxedValue::ValuePrinter<DeleterMarker>(const void *value) {
+  const DeleterMarker* val = reinterpret_cast<const DeleterMarker*>(value);
+  return base::StringPrintf("DeleterMarker:%s",
+                            *val->marker_ ? "true" : "false");
+}
+
+TEST(UmBoxedValueTest, Deleted) {
+  bool marker = true;
+  const DeleterMarker* deleter_marker = new DeleterMarker(&marker);
+
+  EXPECT_FALSE(marker);
+  BoxedValue* box = new BoxedValue(deleter_marker);
+  EXPECT_FALSE(marker);
+  delete box;
+  EXPECT_TRUE(marker);
+}
+
+TEST(UmBoxedValueTest, MoveConstructor) {
+  bool marker = true;
+  const DeleterMarker* deleter_marker = new DeleterMarker(&marker);
+
+  BoxedValue* box = new BoxedValue(deleter_marker);
+  BoxedValue* new_box = new BoxedValue(std::move(*box));
+  // box is now undefined but valid.
+  delete box;
+  EXPECT_FALSE(marker);
+  // The deleter_marker gets deleted at this point.
+  delete new_box;
+  EXPECT_TRUE(marker);
+}
+
+TEST(UmBoxedValueTest, MixedList) {
+  list<BoxedValue> lst;
+  // This is mostly a compile test.
+  lst.emplace_back(new const int{42});
+  lst.emplace_back(new const string("Hello world!"));
+  bool marker;
+  lst.emplace_back(new const DeleterMarker(&marker));
+  EXPECT_FALSE(marker);
+  lst.clear();
+  EXPECT_TRUE(marker);
+}
+
+TEST(UmBoxedValueTest, MixedMap) {
+  map<int, BoxedValue> m;
+  m.emplace(42, BoxedValue(new const string("Hola mundo!")));
+
+  auto it = m.find(42);
+  ASSERT_NE(it, m.end());
+  EXPECT_NE(nullptr, it->second.value());
+  EXPECT_EQ(nullptr, m[33].value());
+}
+
+TEST(UmBoxedValueTest, StringToString) {
+  EXPECT_EQ("Hej Verden!",
+            BoxedValue(new string("Hej Verden!")).ToString());
+}
+
+TEST(UmBoxedValueTest, IntToString) {
+  EXPECT_EQ("42", BoxedValue(new int(42)).ToString());
+}
+
+TEST(UmBoxedValueTest, Int64ToString) {
+  // -123456789012345 doesn't fit in 32-bit integers.
+  EXPECT_EQ("-123456789012345", BoxedValue(
+      new int64_t(-123456789012345LL)).ToString());
+}
+
+TEST(UmBoxedValueTest, UnsignedIntToString) {
+  // 4294967295 is the biggest possible 32-bit unsigned integer.
+  EXPECT_EQ("4294967295",
+            BoxedValue(new unsigned int(4294967295U)).ToString());  // NOLINT
+}
+
+TEST(UmBoxedValueTest, UnsignedInt64ToString) {
+  // 18446744073709551615 is the biggest possible 64-bit unsigned integer.
+  EXPECT_EQ("18446744073709551615", BoxedValue(
+      new uint64_t(18446744073709551615ULL)).ToString());
+}
+
+TEST(UmBoxedValueTest, BoolToString) {
+  EXPECT_EQ("false", BoxedValue(new bool(false)).ToString());
+  EXPECT_EQ("true", BoxedValue(new bool(true)).ToString());
+}
+
+TEST(UmBoxedValueTest, DoubleToString) {
+  EXPECT_EQ("1.501", BoxedValue(new double(1.501)).ToString());
+}
+
+TEST(UmBoxedValueTest, TimeToString) {
+  // Tue Apr 29 22:30:55 UTC 2014 is 1398810655 seconds since the Unix Epoch.
+  EXPECT_EQ("4/29/2014 22:30:55 GMT",
+            BoxedValue(new Time(Time::FromTimeT(1398810655))).ToString());
+}
+
+TEST(UmBoxedValueTest, TimeDeltaToString) {
+  // 12345 seconds is 3 hours, 25 minutes and 45 seconds.
+  EXPECT_EQ("3h25m45s",
+            BoxedValue(new TimeDelta(TimeDelta::FromSeconds(12345)))
+            .ToString());
+}
+
+TEST(UmBoxedValueTest, ConnectionTypeToString) {
+  EXPECT_EQ("Ethernet",
+            BoxedValue(new ConnectionType(ConnectionType::kEthernet))
+            .ToString());
+  EXPECT_EQ("Wifi",
+            BoxedValue(new ConnectionType(ConnectionType::kWifi)).ToString());
+  EXPECT_EQ("Wimax",
+            BoxedValue(new ConnectionType(ConnectionType::kWimax)).ToString());
+  EXPECT_EQ("Bluetooth",
+            BoxedValue(new ConnectionType(ConnectionType::kBluetooth))
+            .ToString());
+  EXPECT_EQ("Cellular",
+            BoxedValue(new ConnectionType(ConnectionType::kCellular))
+            .ToString());
+  EXPECT_EQ("Unknown",
+            BoxedValue(new ConnectionType(ConnectionType::kUnknown))
+            .ToString());
+}
+
+TEST(UmBoxedValueTest, ConnectionTetheringToString) {
+  EXPECT_EQ("Not Detected",
+            BoxedValue(new ConnectionTethering(
+                ConnectionTethering::kNotDetected)).ToString());
+  EXPECT_EQ("Suspected",
+            BoxedValue(new ConnectionTethering(ConnectionTethering::kSuspected))
+            .ToString());
+  EXPECT_EQ("Confirmed",
+            BoxedValue(new ConnectionTethering(ConnectionTethering::kConfirmed))
+            .ToString());
+  EXPECT_EQ("Unknown",
+            BoxedValue(new ConnectionTethering(ConnectionTethering::kUnknown))
+            .ToString());
+}
+
+TEST(UmBoxedValueTest, SetConnectionTypeToString) {
+  set<ConnectionType>* set1 = new set<ConnectionType>;
+  set1->insert(ConnectionType::kWimax);
+  set1->insert(ConnectionType::kEthernet);
+  EXPECT_EQ("Ethernet,Wimax", BoxedValue(set1).ToString());
+
+  set<ConnectionType>* set2 = new set<ConnectionType>;
+  set2->insert(ConnectionType::kWifi);
+  EXPECT_EQ("Wifi", BoxedValue(set2).ToString());
+}
+
+TEST(UmBoxedValueTest, StageToString) {
+  EXPECT_EQ("Idle",
+            BoxedValue(new Stage(Stage::kIdle)).ToString());
+  EXPECT_EQ("Checking For Update",
+            BoxedValue(new Stage(Stage::kCheckingForUpdate)).ToString());
+  EXPECT_EQ("Update Available",
+            BoxedValue(new Stage(Stage::kUpdateAvailable)).ToString());
+  EXPECT_EQ("Downloading",
+            BoxedValue(new Stage(Stage::kDownloading)).ToString());
+  EXPECT_EQ("Verifying",
+            BoxedValue(new Stage(Stage::kVerifying)).ToString());
+  EXPECT_EQ("Finalizing",
+            BoxedValue(new Stage(Stage::kFinalizing)).ToString());
+  EXPECT_EQ("Updated, Need Reboot",
+            BoxedValue(new Stage(Stage::kUpdatedNeedReboot)).ToString());
+  EXPECT_EQ("Reporting Error Event",
+            BoxedValue(new Stage(Stage::kReportingErrorEvent)).ToString());
+  EXPECT_EQ("Attempting Rollback",
+            BoxedValue(new Stage(Stage::kAttemptingRollback)).ToString());
+}
+
+TEST(UmBoxedValueTest, DeleterMarkerToString) {
+  bool marker = false;
+  BoxedValue value = BoxedValue(new DeleterMarker(&marker));
+  EXPECT_EQ("DeleterMarker:false", value.ToString());
+  marker = true;
+  EXPECT_EQ("DeleterMarker:true", value.ToString());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/chromeos_policy.cc b/update_manager/chromeos_policy.cc
new file mode 100644
index 0000000..6ba6f82
--- /dev/null
+++ b/update_manager/chromeos_policy.cc
@@ -0,0 +1,942 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/chromeos_policy.h"
+
+#include <algorithm>
+#include <set>
+#include <string>
+
+#include <base/logging.h>
+#include <base/strings/string_util.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/error_code.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/device_policy_provider.h"
+#include "update_engine/update_manager/policy_utils.h"
+#include "update_engine/update_manager/shill_provider.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::ErrorCode;
+using std::get;
+using std::max;
+using std::min;
+using std::set;
+using std::string;
+
+namespace {
+
+// Examines |err_code| and decides whether the URL index needs to be advanced,
+// the error count for the URL incremented, or none of the above. In the first
+// case, returns true; in the second case, increments |*url_num_error_p| and
+// returns false; otherwise just returns false.
+//
+// TODO(garnold) Adapted from PayloadState::UpdateFailed() (to be retired).
+bool HandleErrorCode(ErrorCode err_code, int* url_num_error_p) {
+  err_code = chromeos_update_engine::utils::GetBaseErrorCode(err_code);
+  switch (err_code) {
+    // Errors which are good indicators of a problem with a particular URL or
+    // the protocol used in the URL or entities in the communication channel
+    // (e.g. proxies). We should try the next available URL in the next update
+    // check to quickly recover from these errors.
+    case ErrorCode::kPayloadHashMismatchError:
+    case ErrorCode::kPayloadSizeMismatchError:
+    case ErrorCode::kDownloadPayloadVerificationError:
+    case ErrorCode::kDownloadPayloadPubKeyVerificationError:
+    case ErrorCode::kSignedDeltaPayloadExpectedError:
+    case ErrorCode::kDownloadInvalidMetadataMagicString:
+    case ErrorCode::kDownloadSignatureMissingInManifest:
+    case ErrorCode::kDownloadManifestParseError:
+    case ErrorCode::kDownloadMetadataSignatureError:
+    case ErrorCode::kDownloadMetadataSignatureVerificationError:
+    case ErrorCode::kDownloadMetadataSignatureMismatch:
+    case ErrorCode::kDownloadOperationHashVerificationError:
+    case ErrorCode::kDownloadOperationExecutionError:
+    case ErrorCode::kDownloadOperationHashMismatch:
+    case ErrorCode::kDownloadInvalidMetadataSize:
+    case ErrorCode::kDownloadInvalidMetadataSignature:
+    case ErrorCode::kDownloadOperationHashMissingError:
+    case ErrorCode::kDownloadMetadataSignatureMissingError:
+    case ErrorCode::kPayloadMismatchedType:
+    case ErrorCode::kUnsupportedMajorPayloadVersion:
+    case ErrorCode::kUnsupportedMinorPayloadVersion:
+      LOG(INFO) << "Advancing download URL due to error "
+                << chromeos_update_engine::utils::CodeToString(err_code)
+                << " (" << static_cast<int>(err_code) << ")";
+      return true;
+
+    // Errors which seem to be just transient network/communication related
+    // failures and do not indicate any inherent problem with the URL itself.
+    // So, we should keep the current URL but just increment the
+    // failure count to give it more chances. This way, while we maximize our
+    // chances of downloading from the URLs that appear earlier in the response
+    // (because download from a local server URL that appears earlier in a
+    // response is preferable than downloading from the next URL which could be
+    // an Internet URL and thus could be more expensive).
+    case ErrorCode::kError:
+    case ErrorCode::kDownloadTransferError:
+    case ErrorCode::kDownloadWriteError:
+    case ErrorCode::kDownloadStateInitializationError:
+    case ErrorCode::kOmahaErrorInHTTPResponse:  // Aggregate for HTTP errors.
+      LOG(INFO) << "Incrementing URL failure count due to error "
+                << chromeos_update_engine::utils::CodeToString(err_code)
+                << " (" << static_cast<int>(err_code) << ")";
+      *url_num_error_p += 1;
+      return false;
+
+    // Errors which are not specific to a URL and hence shouldn't result in
+    // the URL being penalized. This can happen in two cases:
+    // 1. We haven't started downloading anything: These errors don't cost us
+    // anything in terms of actual payload bytes, so we should just do the
+    // regular retries at the next update check.
+    // 2. We have successfully downloaded the payload: In this case, the
+    // payload attempt number would have been incremented and would take care
+    // of the back-off at the next update check.
+    // In either case, there's no need to update URL index or failure count.
+    case ErrorCode::kOmahaRequestError:
+    case ErrorCode::kOmahaResponseHandlerError:
+    case ErrorCode::kPostinstallRunnerError:
+    case ErrorCode::kFilesystemCopierError:
+    case ErrorCode::kInstallDeviceOpenError:
+    case ErrorCode::kKernelDeviceOpenError:
+    case ErrorCode::kDownloadNewPartitionInfoError:
+    case ErrorCode::kNewRootfsVerificationError:
+    case ErrorCode::kNewKernelVerificationError:
+    case ErrorCode::kPostinstallBootedFromFirmwareB:
+    case ErrorCode::kPostinstallFirmwareRONotUpdatable:
+    case ErrorCode::kOmahaRequestEmptyResponseError:
+    case ErrorCode::kOmahaRequestXMLParseError:
+    case ErrorCode::kOmahaResponseInvalid:
+    case ErrorCode::kOmahaUpdateIgnoredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredPerPolicy:
+    case ErrorCode::kOmahaUpdateDeferredForBackoff:
+    case ErrorCode::kPostinstallPowerwashError:
+    case ErrorCode::kUpdateCanceledByChannelChange:
+    case ErrorCode::kOmahaRequestXMLHasEntityDecl:
+    case ErrorCode::kFilesystemVerifierError:
+      LOG(INFO) << "Not changing URL index or failure count due to error "
+                << chromeos_update_engine::utils::CodeToString(err_code)
+                << " (" << static_cast<int>(err_code) << ")";
+      return false;
+
+    case ErrorCode::kSuccess:                            // success code
+    case ErrorCode::kUmaReportedMax:                     // not an error code
+    case ErrorCode::kOmahaRequestHTTPResponseBase:       // aggregated already
+    case ErrorCode::kDevModeFlag:                       // not an error code
+    case ErrorCode::kResumedFlag:                        // not an error code
+    case ErrorCode::kTestImageFlag:                      // not an error code
+    case ErrorCode::kTestOmahaUrlFlag:                   // not an error code
+    case ErrorCode::kSpecialFlags:                       // not an error code
+      // These shouldn't happen. Enumerating these  explicitly here so that we
+      // can let the compiler warn about new error codes that are added to
+      // action_processor.h but not added here.
+      LOG(WARNING) << "Unexpected error "
+                   << chromeos_update_engine::utils::CodeToString(err_code)
+                   << " (" << static_cast<int>(err_code) << ")";
+    // Note: Not adding a default here so as to let the compiler warn us of
+    // any new enums that were added in the .h but not listed in this switch.
+  }
+  return false;
+}
+
+// Checks whether |url| can be used under given download restrictions.
+bool IsUrlUsable(const string& url, bool http_allowed) {
+  return http_allowed || !base::StartsWithASCII(url, "http://", false);
+}
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+const int ChromeOSPolicy::kTimeoutInitialInterval =  7 * 60;
+
+// TODO(deymo): Split the update_manager policies for Brillo and ChromeOS and
+// make the update check periodic interval configurable.
+#ifdef __ANDROID__
+const int ChromeOSPolicy::kTimeoutPeriodicInterval = 5 * 60 * 60;
+const int ChromeOSPolicy::kTimeoutMaxBackoffInterval = 26 * 60 * 60;
+#else
+const int ChromeOSPolicy::kTimeoutPeriodicInterval = 45 * 60;
+const int ChromeOSPolicy::kTimeoutMaxBackoffInterval = 4 * 60 * 60;
+#endif  // __ANDROID__
+
+const int ChromeOSPolicy::kTimeoutRegularFuzz = 10 * 60;
+const int ChromeOSPolicy::kAttemptBackoffMaxIntervalInDays = 16;
+const int ChromeOSPolicy::kAttemptBackoffFuzzInHours = 12;
+const int ChromeOSPolicy::kMaxP2PAttempts = 10;
+const int ChromeOSPolicy::kMaxP2PAttemptsPeriodInSeconds = 5 * 24 * 60 * 60;
+
+EvalStatus ChromeOSPolicy::UpdateCheckAllowed(
+    EvaluationContext* ec, State* state, string* error,
+    UpdateCheckParams* result) const {
+  // Set the default return values.
+  result->updates_enabled = true;
+  result->target_channel.clear();
+  result->target_version_prefix.clear();
+  result->is_interactive = false;
+
+  DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+  UpdaterProvider* const updater_provider = state->updater_provider();
+  SystemProvider* const system_provider = state->system_provider();
+
+  // Do not perform any updates if booted from removable device. This decision
+  // is final.
+  const unsigned int* num_slots_p = ec->GetValue(
+      system_provider->var_num_slots());
+  if (!num_slots_p || *num_slots_p < 2) {
+    LOG(INFO) << "Not enough slots for A/B updates, disabling update checks.";
+    result->updates_enabled = false;
+    return EvalStatus::kSucceeded;
+  }
+
+  const bool* device_policy_is_loaded_p = ec->GetValue(
+      dp_provider->var_device_policy_is_loaded());
+  if (device_policy_is_loaded_p && *device_policy_is_loaded_p) {
+    // Check whether updates are disabled by policy.
+    const bool* update_disabled_p = ec->GetValue(
+        dp_provider->var_update_disabled());
+    if (update_disabled_p && *update_disabled_p) {
+      LOG(INFO) << "Updates disabled by policy, blocking update checks.";
+      return EvalStatus::kAskMeAgainLater;
+    }
+
+    // Determine whether a target version prefix is dictated by policy.
+    const string* target_version_prefix_p = ec->GetValue(
+        dp_provider->var_target_version_prefix());
+    if (target_version_prefix_p)
+      result->target_version_prefix = *target_version_prefix_p;
+
+    // Determine whether a target channel is dictated by policy.
+    const bool* release_channel_delegated_p = ec->GetValue(
+        dp_provider->var_release_channel_delegated());
+    if (release_channel_delegated_p && !(*release_channel_delegated_p)) {
+      const string* release_channel_p = ec->GetValue(
+          dp_provider->var_release_channel());
+      if (release_channel_p)
+        result->target_channel = *release_channel_p;
+    }
+  }
+
+  // First, check to see if an interactive update was requested.
+  const UpdateRequestStatus* forced_update_requested_p = ec->GetValue(
+      updater_provider->var_forced_update_requested());
+  if (forced_update_requested_p &&
+      *forced_update_requested_p != UpdateRequestStatus::kNone) {
+    result->is_interactive =
+        (*forced_update_requested_p == UpdateRequestStatus::kInteractive);
+    LOG(INFO) << "Forced update signaled ("
+              << (result->is_interactive ?  "interactive" : "periodic")
+              << "), allowing update check.";
+    return EvalStatus::kSucceeded;
+  }
+
+  // The logic thereafter applies to periodic updates. Bear in mind that we
+  // should not return a final "no" if any of these criteria are not satisfied,
+  // because the system may still update due to an interactive update request.
+
+  // Unofficial builds should not perform periodic update checks.
+  const bool* is_official_build_p = ec->GetValue(
+      system_provider->var_is_official_build());
+  if (is_official_build_p && !(*is_official_build_p)) {
+    LOG(INFO) << "Unofficial build, blocking periodic update checks.";
+    return EvalStatus::kAskMeAgainLater;
+  }
+
+  // If OOBE is enabled, wait until it is completed.
+  const bool* is_oobe_enabled_p = ec->GetValue(
+      state->config_provider()->var_is_oobe_enabled());
+  if (is_oobe_enabled_p && *is_oobe_enabled_p) {
+    const bool* is_oobe_complete_p = ec->GetValue(
+        system_provider->var_is_oobe_complete());
+    if (is_oobe_complete_p && !(*is_oobe_complete_p)) {
+      LOG(INFO) << "OOBE not completed, blocking update checks.";
+      return EvalStatus::kAskMeAgainLater;
+    }
+  }
+
+  // Ensure that periodic update checks are timed properly.
+  Time next_update_check;
+  if (NextUpdateCheckTime(ec, state, error, &next_update_check) !=
+      EvalStatus::kSucceeded) {
+    return EvalStatus::kFailed;
+  }
+  if (!ec->IsWallclockTimeGreaterThan(next_update_check)) {
+    LOG(INFO) << "Periodic check interval not satisfied, blocking until "
+              << chromeos_update_engine::utils::ToString(next_update_check);
+    return EvalStatus::kAskMeAgainLater;
+  }
+
+  // It is time to check for an update.
+  LOG(INFO) << "Allowing update check.";
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus ChromeOSPolicy::UpdateCanStart(
+    EvaluationContext* ec,
+    State* state,
+    string* error,
+    UpdateDownloadParams* result,
+    const UpdateState update_state) const {
+  // Set the default return values. Note that we set persisted values (backoff,
+  // scattering) to the same values presented in the update state. The reason is
+  // that preemptive returns, such as the case where an update check is due,
+  // should not clear off the said values; rather, it is the deliberate
+  // inference of new values that should cause them to be reset.
+  result->update_can_start = false;
+  result->cannot_start_reason = UpdateCannotStartReason::kUndefined;
+  result->download_url_idx = -1;
+  result->download_url_allowed = true;
+  result->download_url_num_errors = 0;
+  result->p2p_downloading_allowed = false;
+  result->p2p_sharing_allowed = false;
+  result->do_increment_failures = false;
+  result->backoff_expiry = update_state.backoff_expiry;
+  result->scatter_wait_period = update_state.scatter_wait_period;
+  result->scatter_check_threshold = update_state.scatter_check_threshold;
+
+  // Make sure that we're not due for an update check.
+  UpdateCheckParams check_result;
+  EvalStatus check_status = UpdateCheckAllowed(ec, state, error, &check_result);
+  if (check_status == EvalStatus::kFailed)
+    return EvalStatus::kFailed;
+  bool is_check_due = (check_status == EvalStatus::kSucceeded &&
+                       check_result.updates_enabled == true);
+
+  // Check whether backoff applies, and if not then which URL can be used for
+  // downloading. These require scanning the download error log, and so they are
+  // done together.
+  UpdateBackoffAndDownloadUrlResult backoff_url_result;
+  EvalStatus backoff_url_status = UpdateBackoffAndDownloadUrl(
+      ec, state, error, &backoff_url_result, update_state);
+  if (backoff_url_status == EvalStatus::kFailed)
+    return EvalStatus::kFailed;
+  result->download_url_idx = backoff_url_result.url_idx;
+  result->download_url_num_errors = backoff_url_result.url_num_errors;
+  result->do_increment_failures = backoff_url_result.do_increment_failures;
+  result->backoff_expiry = backoff_url_result.backoff_expiry;
+  bool is_backoff_active =
+      (backoff_url_status == EvalStatus::kAskMeAgainLater) ||
+      !backoff_url_result.backoff_expiry.is_null();
+
+  DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+  bool is_scattering_active = false;
+  EvalStatus scattering_status = EvalStatus::kSucceeded;
+
+  const bool* device_policy_is_loaded_p = ec->GetValue(
+      dp_provider->var_device_policy_is_loaded());
+  if (device_policy_is_loaded_p && *device_policy_is_loaded_p) {
+    // Check whether scattering applies to this update attempt. We should not be
+    // scattering if this is an interactive update check, or if OOBE is enabled
+    // but not completed.
+    //
+    // Note: current code further suppresses scattering if a "deadline"
+    // attribute is found in the Omaha response. However, it appears that the
+    // presence of this attribute is merely indicative of an OOBE update, during
+    // which we suppress scattering anyway.
+    bool is_scattering_applicable = false;
+    result->scatter_wait_period = kZeroInterval;
+    result->scatter_check_threshold = 0;
+    if (!update_state.is_interactive) {
+      const bool* is_oobe_enabled_p = ec->GetValue(
+          state->config_provider()->var_is_oobe_enabled());
+      if (is_oobe_enabled_p && !(*is_oobe_enabled_p)) {
+        is_scattering_applicable = true;
+      } else {
+        const bool* is_oobe_complete_p = ec->GetValue(
+            state->system_provider()->var_is_oobe_complete());
+        is_scattering_applicable = (is_oobe_complete_p && *is_oobe_complete_p);
+      }
+    }
+
+    // Compute scattering values.
+    if (is_scattering_applicable) {
+      UpdateScatteringResult scatter_result;
+      scattering_status = UpdateScattering(ec, state, error, &scatter_result,
+                                           update_state);
+      if (scattering_status == EvalStatus::kFailed) {
+        return EvalStatus::kFailed;
+      } else {
+        result->scatter_wait_period = scatter_result.wait_period;
+        result->scatter_check_threshold = scatter_result.check_threshold;
+        if (scattering_status == EvalStatus::kAskMeAgainLater ||
+            scatter_result.is_scattering)
+          is_scattering_active = true;
+      }
+    }
+  }
+
+  // Find out whether P2P is globally enabled.
+  bool p2p_enabled;
+  EvalStatus p2p_enabled_status = P2PEnabled(ec, state, error, &p2p_enabled);
+  if (p2p_enabled_status != EvalStatus::kSucceeded)
+    return EvalStatus::kFailed;
+
+  // Is P2P is enabled, consider allowing it for downloading and/or sharing.
+  if (p2p_enabled) {
+    // Sharing via P2P is allowed if not disabled by Omaha.
+    if (update_state.p2p_sharing_disabled) {
+      LOG(INFO) << "Blocked P2P sharing because it is disabled by Omaha.";
+    } else {
+      result->p2p_sharing_allowed = true;
+    }
+
+    // Downloading via P2P is allowed if not disabled by Omaha, an update is not
+    // interactive, and other limits haven't been reached.
+    if (update_state.p2p_downloading_disabled) {
+      LOG(INFO) << "Blocked P2P downloading because it is disabled by Omaha.";
+    } else if (update_state.is_interactive) {
+      LOG(INFO) << "Blocked P2P downloading because update is interactive.";
+    } else if (update_state.p2p_num_attempts >= kMaxP2PAttempts) {
+      LOG(INFO) << "Blocked P2P downloading as it was attempted too many "
+                   "times.";
+    } else if (!update_state.p2p_first_attempted.is_null() &&
+               ec->IsWallclockTimeGreaterThan(
+                   update_state.p2p_first_attempted +
+                   TimeDelta::FromSeconds(kMaxP2PAttemptsPeriodInSeconds))) {
+      LOG(INFO) << "Blocked P2P downloading as its usage timespan exceeds "
+                   "limit.";
+    } else {
+      // P2P download is allowed; if backoff or scattering are active, be sure
+      // to suppress them, yet prevent any download URL from being used.
+      result->p2p_downloading_allowed = true;
+      if (is_backoff_active || is_scattering_active) {
+        is_backoff_active = is_scattering_active = false;
+        result->download_url_allowed = false;
+      }
+    }
+  }
+
+  // Check for various deterrents.
+  if (is_check_due) {
+    result->cannot_start_reason = UpdateCannotStartReason::kCheckDue;
+    return EvalStatus::kSucceeded;
+  }
+  if (is_backoff_active) {
+    result->cannot_start_reason = UpdateCannotStartReason::kBackoff;
+    return backoff_url_status;
+  }
+  if (is_scattering_active) {
+    result->cannot_start_reason = UpdateCannotStartReason::kScattering;
+    return scattering_status;
+  }
+  if (result->download_url_idx < 0 && !result->p2p_downloading_allowed) {
+    result->cannot_start_reason = UpdateCannotStartReason::kCannotDownload;
+    return EvalStatus::kSucceeded;
+  }
+
+  // Update is good to go.
+  result->update_can_start = true;
+  return EvalStatus::kSucceeded;
+}
+
+// TODO(garnold) Logic in this method is based on
+// ConnectionManager::IsUpdateAllowedOver(); be sure to deprecate the latter.
+//
+// TODO(garnold) The current logic generally treats the list of allowed
+// connections coming from the device policy as a whitelist, meaning that it
+// can only be used for enabling connections, but not disable them. Further,
+// certain connection types (like Bluetooth) cannot be enabled even by policy.
+// In effect, the only thing that device policy can change is to enable
+// updates over a cellular network (disabled by default). We may want to
+// revisit this semantics, allowing greater flexibility in defining specific
+// permissions over all types of networks.
+EvalStatus ChromeOSPolicy::UpdateDownloadAllowed(
+    EvaluationContext* ec,
+    State* state,
+    string* error,
+    bool* result) const {
+  // Get the current connection type.
+  ShillProvider* const shill_provider = state->shill_provider();
+  const ConnectionType* conn_type_p = ec->GetValue(
+      shill_provider->var_conn_type());
+  POLICY_CHECK_VALUE_AND_FAIL(conn_type_p, error);
+  ConnectionType conn_type = *conn_type_p;
+
+  // If we're tethering, treat it as a cellular connection.
+  if (conn_type != ConnectionType::kCellular) {
+    const ConnectionTethering* conn_tethering_p = ec->GetValue(
+        shill_provider->var_conn_tethering());
+    POLICY_CHECK_VALUE_AND_FAIL(conn_tethering_p, error);
+    if (*conn_tethering_p == ConnectionTethering::kConfirmed)
+      conn_type = ConnectionType::kCellular;
+  }
+
+  // By default, we allow updates for all connection types, with exceptions as
+  // noted below. This also determines whether a device policy can override the
+  // default.
+  *result = true;
+  bool device_policy_can_override = false;
+  switch (conn_type) {
+    case ConnectionType::kBluetooth:
+      *result = false;
+      break;
+
+    case ConnectionType::kCellular:
+      *result = false;
+      device_policy_can_override = true;
+      break;
+
+    case ConnectionType::kUnknown:
+      if (error)
+        *error = "Unknown connection type";
+      return EvalStatus::kFailed;
+
+    default:
+      break;  // Nothing to do.
+  }
+
+  // If update is allowed, we're done.
+  if (*result)
+    return EvalStatus::kSucceeded;
+
+  // Check whether the device policy specifically allows this connection.
+  if (device_policy_can_override) {
+    DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+    const bool* device_policy_is_loaded_p = ec->GetValue(
+        dp_provider->var_device_policy_is_loaded());
+    if (device_policy_is_loaded_p && *device_policy_is_loaded_p) {
+      const set<ConnectionType>* allowed_conn_types_p = ec->GetValue(
+          dp_provider->var_allowed_connection_types_for_update());
+      if (allowed_conn_types_p) {
+        if (allowed_conn_types_p->count(conn_type)) {
+          *result = true;
+          return EvalStatus::kSucceeded;
+        }
+      } else if (conn_type == ConnectionType::kCellular) {
+        // Local user settings can allow updates over cellular iff a policy was
+        // loaded but no allowed connections were specified in it.
+        const bool* update_over_cellular_allowed_p = ec->GetValue(
+            state->updater_provider()->var_cellular_enabled());
+        if (update_over_cellular_allowed_p && *update_over_cellular_allowed_p)
+          *result = true;
+      }
+    }
+  }
+
+  return (*result ? EvalStatus::kSucceeded : EvalStatus::kAskMeAgainLater);
+}
+
+EvalStatus ChromeOSPolicy::P2PEnabled(EvaluationContext* ec,
+                                      State* state,
+                                      string* error,
+                                      bool* result) const {
+  bool enabled = false;
+
+  // Determine whether use of P2P is allowed by policy. Even if P2P is not
+  // explicitly allowed, we allow it if the device is enterprise enrolled (that
+  // is, missing or empty owner string).
+  DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+  const bool* device_policy_is_loaded_p = ec->GetValue(
+      dp_provider->var_device_policy_is_loaded());
+  if (device_policy_is_loaded_p && *device_policy_is_loaded_p) {
+    const bool* policy_au_p2p_enabled_p = ec->GetValue(
+        dp_provider->var_au_p2p_enabled());
+    if (policy_au_p2p_enabled_p) {
+      enabled = *policy_au_p2p_enabled_p;
+    } else {
+      const string* policy_owner_p = ec->GetValue(dp_provider->var_owner());
+      if (!policy_owner_p || policy_owner_p->empty())
+        enabled = true;
+    }
+  }
+
+  // Enable P2P, if so mandated by the updater configuration. This is additive
+  // to whether or not P2P is enabled by device policy.
+  if (!enabled) {
+    const bool* updater_p2p_enabled_p = ec->GetValue(
+        state->updater_provider()->var_p2p_enabled());
+    enabled = updater_p2p_enabled_p && *updater_p2p_enabled_p;
+  }
+
+  *result = enabled;
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus ChromeOSPolicy::P2PEnabledChanged(EvaluationContext* ec,
+                                             State* state,
+                                             string* error,
+                                             bool* result,
+                                             bool prev_result) const {
+  EvalStatus status = P2PEnabled(ec, state, error, result);
+  if (status == EvalStatus::kSucceeded && *result == prev_result)
+    return EvalStatus::kAskMeAgainLater;
+  return status;
+}
+
+EvalStatus ChromeOSPolicy::NextUpdateCheckTime(EvaluationContext* ec,
+                                               State* state, string* error,
+                                               Time* next_update_check) const {
+  UpdaterProvider* const updater_provider = state->updater_provider();
+
+  // Don't check for updates too often. We limit the update checks to once every
+  // some interval. The interval is kTimeoutInitialInterval the first time and
+  // kTimeoutPeriodicInterval for the subsequent update checks. If the update
+  // check fails, we increase the interval between the update checks
+  // exponentially until kTimeoutMaxBackoffInterval. Finally, to avoid having
+  // many chromebooks running update checks at the exact same time, we add some
+  // fuzz to the interval.
+  const Time* updater_started_time =
+      ec->GetValue(updater_provider->var_updater_started_time());
+  POLICY_CHECK_VALUE_AND_FAIL(updater_started_time, error);
+
+  const Time* last_checked_time =
+      ec->GetValue(updater_provider->var_last_checked_time());
+
+  const uint64_t* seed = ec->GetValue(state->random_provider()->var_seed());
+  POLICY_CHECK_VALUE_AND_FAIL(seed, error);
+
+  PRNG prng(*seed);
+
+  // If this is the first attempt, compute and return an initial value.
+  if (!last_checked_time || *last_checked_time < *updater_started_time) {
+    *next_update_check = *updater_started_time + FuzzedInterval(
+        &prng, kTimeoutInitialInterval, kTimeoutRegularFuzz);
+    return EvalStatus::kSucceeded;
+  }
+
+  // Check whether the server is enforcing a poll interval; if not, this value
+  // will be zero.
+  const unsigned int* server_dictated_poll_interval = ec->GetValue(
+      updater_provider->var_server_dictated_poll_interval());
+  POLICY_CHECK_VALUE_AND_FAIL(server_dictated_poll_interval, error);
+
+  int interval = *server_dictated_poll_interval;
+  int fuzz = 0;
+
+  // If no poll interval was dictated by server compute a back-off period,
+  // starting from a predetermined base periodic interval and increasing
+  // exponentially by the number of consecutive failed attempts.
+  if (interval == 0) {
+    const unsigned int* consecutive_failed_update_checks = ec->GetValue(
+        updater_provider->var_consecutive_failed_update_checks());
+    POLICY_CHECK_VALUE_AND_FAIL(consecutive_failed_update_checks, error);
+
+    interval = kTimeoutPeriodicInterval;
+    unsigned int num_failures = *consecutive_failed_update_checks;
+    while (interval < kTimeoutMaxBackoffInterval && num_failures) {
+      interval *= 2;
+      num_failures--;
+    }
+  }
+
+  // We cannot back off longer than the predetermined maximum interval.
+  if (interval > kTimeoutMaxBackoffInterval)
+    interval = kTimeoutMaxBackoffInterval;
+
+  // We cannot back off shorter than the predetermined periodic interval. Also,
+  // in this case set the fuzz to a predetermined regular value.
+  if (interval <= kTimeoutPeriodicInterval) {
+    interval = kTimeoutPeriodicInterval;
+    fuzz = kTimeoutRegularFuzz;
+  }
+
+  // If not otherwise determined, defer to a fuzz of +/-(interval / 2).
+  if (fuzz == 0)
+    fuzz = interval;
+
+  *next_update_check = *last_checked_time + FuzzedInterval(
+      &prng, interval, fuzz);
+  return EvalStatus::kSucceeded;
+}
+
+TimeDelta ChromeOSPolicy::FuzzedInterval(PRNG* prng, int interval, int fuzz) {
+  DCHECK_GE(interval, 0);
+  DCHECK_GE(fuzz, 0);
+  int half_fuzz = fuzz / 2;
+  // This guarantees the output interval is non negative.
+  int interval_min = max(interval - half_fuzz, 0);
+  int interval_max = interval + half_fuzz;
+  return TimeDelta::FromSeconds(prng->RandMinMax(interval_min, interval_max));
+}
+
+EvalStatus ChromeOSPolicy::UpdateBackoffAndDownloadUrl(
+    EvaluationContext* ec, State* state, string* error,
+    UpdateBackoffAndDownloadUrlResult* result,
+    const UpdateState& update_state) const {
+  // Sanity checks.
+  DCHECK_GE(update_state.download_errors_max, 0);
+
+  // Set default result values.
+  result->do_increment_failures = false;
+  result->backoff_expiry = update_state.backoff_expiry;
+  result->url_idx = -1;
+  result->url_num_errors = 0;
+
+  const bool* is_official_build_p = ec->GetValue(
+      state->system_provider()->var_is_official_build());
+  bool is_official_build = (is_official_build_p ? *is_official_build_p : true);
+
+  // Check whether backoff is enabled.
+  bool may_backoff = false;
+  if (update_state.is_backoff_disabled) {
+    LOG(INFO) << "Backoff disabled by Omaha.";
+  } else if (update_state.is_interactive) {
+    LOG(INFO) << "No backoff for interactive updates.";
+  } else if (update_state.is_delta_payload) {
+    LOG(INFO) << "No backoff for delta payloads.";
+  } else if (!is_official_build) {
+    LOG(INFO) << "No backoff for unofficial builds.";
+  } else {
+    may_backoff = true;
+  }
+
+  // If previous backoff still in effect, block.
+  if (may_backoff && !update_state.backoff_expiry.is_null() &&
+      !ec->IsWallclockTimeGreaterThan(update_state.backoff_expiry)) {
+    LOG(INFO) << "Previous backoff has not expired, waiting.";
+    return EvalStatus::kAskMeAgainLater;
+  }
+
+  // Determine whether HTTP downloads are forbidden by policy. This only
+  // applies to official system builds; otherwise, HTTP is always enabled.
+  bool http_allowed = true;
+  if (is_official_build) {
+    DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+    const bool* device_policy_is_loaded_p = ec->GetValue(
+        dp_provider->var_device_policy_is_loaded());
+    if (device_policy_is_loaded_p && *device_policy_is_loaded_p) {
+      const bool* policy_http_downloads_enabled_p = ec->GetValue(
+          dp_provider->var_http_downloads_enabled());
+      http_allowed = (!policy_http_downloads_enabled_p ||
+                      *policy_http_downloads_enabled_p);
+    }
+  }
+
+  int url_idx = update_state.last_download_url_idx;
+  if (url_idx < 0)
+    url_idx = -1;
+  bool do_advance_url = false;
+  bool is_failure_occurred = false;
+  Time err_time;
+
+  // Scan the relevant part of the download error log, tracking which URLs are
+  // being used, and accounting the number of errors for each URL. Note that
+  // this process may not traverse all errors provided, as it may decide to bail
+  // out midway depending on the particular errors exhibited, the number of
+  // failures allowed, etc. When this ends, |url_idx| will point to the last URL
+  // used (-1 if starting fresh), |do_advance_url| will determine whether the
+  // URL needs to be advanced, and |err_time| the point in time when the last
+  // reported error occurred.  Additionally, if the error log indicates that an
+  // update attempt has failed (abnormal), then |is_failure_occurred| will be
+  // set to true.
+  const int num_urls = update_state.download_urls.size();
+  int prev_url_idx = -1;
+  int url_num_errors = update_state.last_download_url_num_errors;
+  Time prev_err_time;
+  bool is_first = true;
+  for (const auto& err_tuple : update_state.download_errors) {
+    // Do some sanity checks.
+    int used_url_idx = get<0>(err_tuple);
+    if (is_first && url_idx >= 0 && used_url_idx != url_idx) {
+      LOG(WARNING) << "First URL in error log (" << used_url_idx
+                   << ") not as expected (" << url_idx << ")";
+    }
+    is_first = false;
+    url_idx = used_url_idx;
+    if (url_idx < 0 || url_idx >= num_urls) {
+      LOG(ERROR) << "Download error log contains an invalid URL index ("
+                 << url_idx << ")";
+      return EvalStatus::kFailed;
+    }
+    err_time = get<2>(err_tuple);
+    if (!(prev_err_time.is_null() || err_time >= prev_err_time)) {
+      // TODO(garnold) Monotonicity cannot really be assumed when dealing with
+      // wallclock-based timestamps. However, we're making a simplifying
+      // assumption so as to keep the policy implementation straightforward, for
+      // now. In general, we should convert all timestamp handling in the
+      // UpdateManager to use monotonic time (instead of wallclock), including
+      // the computation of various expiration times (backoff, scattering, etc).
+      // The client will do whatever conversions necessary when
+      // persisting/retrieving these values across reboots. See chromium:408794.
+      LOG(ERROR) << "Download error timestamps not monotonically increasing.";
+      return EvalStatus::kFailed;
+    }
+    prev_err_time = err_time;
+
+    // Ignore errors that happened before the last known failed attempt.
+    if (!update_state.failures_last_updated.is_null() &&
+        err_time <= update_state.failures_last_updated)
+      continue;
+
+    if (prev_url_idx >= 0) {
+      if (url_idx < prev_url_idx) {
+        LOG(ERROR) << "The URLs in the download error log have wrapped around ("
+                   << prev_url_idx << "->" << url_idx
+                   << "). This should not have happened and means that there's "
+                      "a bug. To be conservative, we record a failed attempt "
+                      "(invalidating the rest of the error log) and resume "
+                      "download from the first usable URL.";
+        url_idx = -1;
+        is_failure_occurred = true;
+        break;
+      }
+
+      if (url_idx > prev_url_idx) {
+        url_num_errors = 0;
+        do_advance_url = false;
+      }
+    }
+
+    if (HandleErrorCode(get<1>(err_tuple), &url_num_errors) ||
+        url_num_errors > update_state.download_errors_max)
+      do_advance_url = true;
+
+    prev_url_idx = url_idx;
+  }
+
+  // If required, advance to the next usable URL. If the URLs wraparound, we
+  // mark an update attempt failure. Also be sure to set the download error
+  // count to zero.
+  if (url_idx < 0 || do_advance_url) {
+    url_num_errors = 0;
+    int start_url_idx = -1;
+    do {
+      if (++url_idx == num_urls) {
+        url_idx = 0;
+        // We only mark failure if an actual advancing of a URL was required.
+        if (do_advance_url)
+          is_failure_occurred = true;
+      }
+
+      if (start_url_idx < 0)
+        start_url_idx = url_idx;
+      else if (url_idx == start_url_idx)
+        url_idx = -1;  // No usable URL.
+    } while (url_idx >= 0 &&
+             !IsUrlUsable(update_state.download_urls[url_idx], http_allowed));
+  }
+
+  // If we have a download URL but a failure was observed, compute a new backoff
+  // expiry (if allowed). The backoff period is generally 2 ^ (num_failures - 1)
+  // days, bounded by the size of int and kAttemptBackoffMaxIntervalInDays, and
+  // fuzzed by kAttemptBackoffFuzzInHours hours. Backoff expiry is computed from
+  // the latest recorded time of error.
+  Time backoff_expiry;
+  if (url_idx >= 0 && is_failure_occurred && may_backoff) {
+    CHECK(!err_time.is_null())
+        << "We must have an error timestamp if a failure occurred!";
+    const uint64_t* seed = ec->GetValue(state->random_provider()->var_seed());
+    POLICY_CHECK_VALUE_AND_FAIL(seed, error);
+    PRNG prng(*seed);
+    int exp = min(update_state.num_failures,
+                       static_cast<int>(sizeof(int)) * 8 - 2);
+    TimeDelta backoff_interval = TimeDelta::FromDays(
+        min(1 << exp, kAttemptBackoffMaxIntervalInDays));
+    TimeDelta backoff_fuzz = TimeDelta::FromHours(kAttemptBackoffFuzzInHours);
+    TimeDelta wait_period = FuzzedInterval(&prng, backoff_interval.InSeconds(),
+                                           backoff_fuzz.InSeconds());
+    backoff_expiry = err_time + wait_period;
+
+    // If the newly computed backoff already expired, nullify it.
+    if (ec->IsWallclockTimeGreaterThan(backoff_expiry))
+      backoff_expiry = Time();
+  }
+
+  result->do_increment_failures = is_failure_occurred;
+  result->backoff_expiry = backoff_expiry;
+  result->url_idx = url_idx;
+  result->url_num_errors = url_num_errors;
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus ChromeOSPolicy::UpdateScattering(
+    EvaluationContext* ec,
+    State* state,
+    string* error,
+    UpdateScatteringResult* result,
+    const UpdateState& update_state) const {
+  // Preconditions. These stem from the postconditions and usage contract.
+  DCHECK(update_state.scatter_wait_period >= kZeroInterval);
+  DCHECK_GE(update_state.scatter_check_threshold, 0);
+
+  // Set default result values.
+  result->is_scattering = false;
+  result->wait_period = kZeroInterval;
+  result->check_threshold = 0;
+
+  DevicePolicyProvider* const dp_provider = state->device_policy_provider();
+
+  // Ensure that a device policy is loaded.
+  const bool* device_policy_is_loaded_p = ec->GetValue(
+      dp_provider->var_device_policy_is_loaded());
+  if (!(device_policy_is_loaded_p && *device_policy_is_loaded_p))
+    return EvalStatus::kSucceeded;
+
+  // Is scattering enabled by policy?
+  const TimeDelta* scatter_factor_p = ec->GetValue(
+      dp_provider->var_scatter_factor());
+  if (!scatter_factor_p || *scatter_factor_p == kZeroInterval)
+    return EvalStatus::kSucceeded;
+
+  // Obtain a pseudo-random number generator.
+  const uint64_t* seed = ec->GetValue(state->random_provider()->var_seed());
+  POLICY_CHECK_VALUE_AND_FAIL(seed, error);
+  PRNG prng(*seed);
+
+  // Step 1: Maintain the scattering wait period.
+  //
+  // If no wait period was previously determined, or it no longer fits in the
+  // scatter factor, then generate a new one. Otherwise, keep the one we have.
+  TimeDelta wait_period = update_state.scatter_wait_period;
+  if (wait_period == kZeroInterval || wait_period > *scatter_factor_p) {
+    wait_period = TimeDelta::FromSeconds(
+        prng.RandMinMax(1, scatter_factor_p->InSeconds()));
+  }
+
+  // If we surpassed the wait period or the max scatter period associated with
+  // the update, then no wait is needed.
+  Time wait_expires = (update_state.first_seen +
+                       min(wait_period, update_state.scatter_wait_period_max));
+  if (ec->IsWallclockTimeGreaterThan(wait_expires))
+    wait_period = kZeroInterval;
+
+  // Step 2: Maintain the update check threshold count.
+  //
+  // If an update check threshold is not specified then generate a new
+  // one.
+  int check_threshold = update_state.scatter_check_threshold;
+  if (check_threshold == 0) {
+    check_threshold = prng.RandMinMax(
+        update_state.scatter_check_threshold_min,
+        update_state.scatter_check_threshold_max);
+  }
+
+  // If the update check threshold is not within allowed range then nullify it.
+  // TODO(garnold) This is compliant with current logic found in
+  // OmahaRequestAction::IsUpdateCheckCountBasedWaitingSatisfied(). We may want
+  // to change it so that it behaves similarly to the wait period case, namely
+  // if the current value exceeds the maximum, we set a new one within range.
+  if (check_threshold > update_state.scatter_check_threshold_max)
+    check_threshold = 0;
+
+  // If the update check threshold is non-zero and satisfied, then nullify it.
+  if (check_threshold > 0 && update_state.num_checks >= check_threshold)
+    check_threshold = 0;
+
+  bool is_scattering = (wait_period != kZeroInterval || check_threshold);
+  EvalStatus ret = EvalStatus::kSucceeded;
+  if (is_scattering && wait_period == update_state.scatter_wait_period &&
+      check_threshold == update_state.scatter_check_threshold)
+    ret = EvalStatus::kAskMeAgainLater;
+  result->is_scattering = is_scattering;
+  result->wait_period = wait_period;
+  result->check_threshold = check_threshold;
+  return ret;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/chromeos_policy.h b/update_manager/chromeos_policy.h
new file mode 100644
index 0000000..b4370c4
--- /dev/null
+++ b/update_manager/chromeos_policy.h
@@ -0,0 +1,203 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_CHROMEOS_POLICY_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_CHROMEOS_POLICY_H_
+
+#include <string>
+
+#include <base/time/time.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/prng.h"
+
+namespace chromeos_update_manager {
+
+// Output information from UpdateBackoffAndDownloadUrl.
+struct UpdateBackoffAndDownloadUrlResult {
+  // Whether the failed attempt count (maintained by the caller) needs to be
+  // incremented.
+  bool do_increment_failures;
+  // The current backoff expiry. Null if backoff is not in effect.
+  base::Time backoff_expiry;
+  // The new URL index to use and number of download errors associated with it.
+  // Significant iff |do_increment_failures| is false and |backoff_expiry| is
+  // null. Negative value means no usable URL was found.
+  int url_idx;
+  int url_num_errors;
+};
+
+// Parameters for update scattering, as returned by UpdateScattering.
+struct UpdateScatteringResult {
+  bool is_scattering;
+  base::TimeDelta wait_period;
+  int check_threshold;
+};
+
+// ChromeOSPolicy implements the policy-related logic used in ChromeOS.
+class ChromeOSPolicy : public Policy {
+ public:
+  ChromeOSPolicy() {}
+  ~ChromeOSPolicy() override {}
+
+  // Policy overrides.
+  EvalStatus UpdateCheckAllowed(
+      EvaluationContext* ec, State* state, std::string* error,
+      UpdateCheckParams* result) const override;
+
+  EvalStatus UpdateCanStart(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      UpdateDownloadParams* result,
+      UpdateState update_state) const override;
+
+  EvalStatus UpdateDownloadAllowed(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      bool* result) const override;
+
+  EvalStatus P2PEnabled(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      bool* result) const override;
+
+  EvalStatus P2PEnabledChanged(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      bool* result,
+      bool prev_result) const override;
+
+ protected:
+  // Policy override.
+  std::string PolicyName() const override { return "ChromeOSPolicy"; }
+
+ private:
+  friend class UmChromeOSPolicyTest;
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              FirstCheckIsAtMostInitialIntervalAfterStart);
+  FRIEND_TEST(UmChromeOSPolicyTest, RecurringCheckBaseIntervalAndFuzz);
+  FRIEND_TEST(UmChromeOSPolicyTest, RecurringCheckBackoffIntervalAndFuzz);
+  FRIEND_TEST(UmChromeOSPolicyTest, RecurringCheckServerDictatedPollInterval);
+  FRIEND_TEST(UmChromeOSPolicyTest, ExponentialBackoffIsCapped);
+  FRIEND_TEST(UmChromeOSPolicyTest, UpdateCheckAllowedWaitsForTheTimeout);
+  FRIEND_TEST(UmChromeOSPolicyTest, UpdateCheckAllowedWaitsForOOBE);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartNotAllowedScatteringNewWaitPeriodApplies);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartNotAllowedScatteringPrevWaitPeriodStillApplies);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartNotAllowedScatteringNewCountThresholdApplies);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartNotAllowedScatteringPrevCountThresholdStillApplies);
+  FRIEND_TEST(UmChromeOSPolicyTest, UpdateCanStartAllowedScatteringSatisfied);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartAllowedInteractivePreventsScattering);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartAllowedP2PDownloadingBlockedDueToNumAttempts);
+  FRIEND_TEST(UmChromeOSPolicyTest,
+              UpdateCanStartAllowedP2PDownloadingBlockedDueToAttemptsPeriod);
+
+  // Auxiliary constant (zero by default).
+  const base::TimeDelta kZeroInterval;
+
+  // Default update check timeout interval/fuzz values used to compute the
+  // NextUpdateCheckTime(), in seconds. Actual fuzz is within +/- half of the
+  // indicated value.
+  static const int kTimeoutInitialInterval;
+  static const int kTimeoutPeriodicInterval;
+  static const int kTimeoutMaxBackoffInterval;
+  static const int kTimeoutRegularFuzz;
+
+  // Maximum update attempt backoff interval and fuzz.
+  static const int kAttemptBackoffMaxIntervalInDays;
+  static const int kAttemptBackoffFuzzInHours;
+
+  // Maximum number of times we'll allow using P2P for the same update payload.
+  static const int kMaxP2PAttempts;
+  // Maximum period of time allowed for download a payload via P2P, in seconds.
+  static const int kMaxP2PAttemptsPeriodInSeconds;
+
+  // A private policy implementation returning the wallclock timestamp when
+  // the next update check should happen.
+  // TODO(garnold) We should probably change that to infer a monotonic
+  // timestamp, which will make the update check intervals more resilient to
+  // clock skews. Might require switching some of the variables exported by the
+  // UpdaterProvider to report monotonic time, as well.
+  EvalStatus NextUpdateCheckTime(EvaluationContext* ec, State* state,
+                                 std::string* error,
+                                 base::Time* next_update_check) const;
+
+  // Returns a TimeDelta based on the provided |interval| seconds +/- half
+  // |fuzz| seconds. The return value is guaranteed to be a non-negative
+  // TimeDelta.
+  static base::TimeDelta FuzzedInterval(PRNG* prng, int interval, int fuzz);
+
+  // A private policy for determining backoff and the download URL to use.
+  // Within |update_state|, |backoff_expiry| and |is_backoff_disabled| are used
+  // for determining whether backoff is still in effect; if not,
+  // |download_errors| is scanned past |failures_last_updated|, and a new
+  // download URL from |download_urls| is found and written to |result->url_idx|
+  // (-1 means no usable URL exists); |download_errors_max| determines the
+  // maximum number of attempts per URL, according to the Omaha response. If an
+  // update failure is identified then |result->do_increment_failures| is set to
+  // true; if backoff is enabled, a new backoff period is computed (from the
+  // time of failure) based on |num_failures|. Otherwise, backoff expiry is
+  // nullified, indicating that no backoff is in effect.
+  //
+  // If backing off but the previous backoff expiry is unchanged, returns
+  // |EvalStatus::kAskMeAgainLater|. Otherwise:
+  //
+  // * If backing off with a new expiry time, then |result->backoff_expiry| is
+  //   set to this time.
+  //
+  // * Else, |result->backoff_expiry| is set to null, indicating that no backoff
+  //   is in effect.
+  //
+  // In any of these cases, returns |EvalStatus::kSucceeded|. If an error
+  // occurred, returns |EvalStatus::kFailed|.
+  EvalStatus UpdateBackoffAndDownloadUrl(
+      EvaluationContext* ec, State* state, std::string* error,
+      UpdateBackoffAndDownloadUrlResult* result,
+      const UpdateState& update_state) const;
+
+  // A private policy for checking whether scattering is due. Writes in |result|
+  // the decision as to whether or not to scatter; a wallclock-based scatter
+  // wait period, which ranges from zero (do not wait) and no greater than the
+  // current scatter factor provided by the device policy (if available) or the
+  // maximum wait period determined by Omaha; and an update check-based
+  // threshold between zero (no threshold) and the maximum number determined by
+  // the update engine. Within |update_state|, |scatter_wait_period| should
+  // contain the last scattering period returned by this function, or zero if no
+  // wait period is known; |scatter_check_threshold| is the last update check
+  // threshold, or zero if no such threshold is known. If not scattering, or if
+  // any of the scattering values has changed, returns |EvalStatus::kSucceeded|;
+  // otherwise, |EvalStatus::kAskMeAgainLater|.
+  EvalStatus UpdateScattering(EvaluationContext* ec, State* state,
+                              std::string* error,
+                              UpdateScatteringResult* result,
+                              const UpdateState& update_state) const;
+
+  DISALLOW_COPY_AND_ASSIGN(ChromeOSPolicy);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_CHROMEOS_POLICY_H_
diff --git a/update_manager/chromeos_policy_unittest.cc b/update_manager/chromeos_policy_unittest.cc
new file mode 100644
index 0000000..a78257d
--- /dev/null
+++ b/update_manager/chromeos_policy_unittest.cc
@@ -0,0 +1,1618 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/chromeos_policy.h"
+
+#include <set>
+#include <string>
+#include <tuple>
+#include <vector>
+
+#include <base/time/time.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/update_manager/evaluation_context.h"
+#include "update_engine/update_manager/fake_state.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::ErrorCode;
+using chromeos_update_engine::FakeClock;
+using std::set;
+using std::string;
+using std::tuple;
+using std::vector;
+
+namespace chromeos_update_manager {
+
+class UmChromeOSPolicyTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    SetUpDefaultClock();
+    eval_ctx_ = new EvaluationContext(&fake_clock_, TimeDelta::FromSeconds(5));
+    SetUpDefaultState();
+    SetUpDefaultDevicePolicy();
+  }
+
+  void TearDown() override {
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  // Sets the clock to fixed values.
+  void SetUpDefaultClock() {
+    fake_clock_.SetMonotonicTime(Time::FromInternalValue(12345678L));
+    fake_clock_.SetWallclockTime(Time::FromInternalValue(12345678901234L));
+  }
+
+  void SetUpDefaultState() {
+    fake_state_.updater_provider()->var_updater_started_time()->reset(
+        new Time(fake_clock_.GetWallclockTime()));
+    fake_state_.updater_provider()->var_last_checked_time()->reset(
+        new Time(fake_clock_.GetWallclockTime()));
+    fake_state_.updater_provider()->var_consecutive_failed_update_checks()->
+        reset(new unsigned int{0});
+    fake_state_.updater_provider()->var_server_dictated_poll_interval()->
+        reset(new unsigned int{0});
+    fake_state_.updater_provider()->var_forced_update_requested()->
+        reset(new UpdateRequestStatus{UpdateRequestStatus::kNone});
+
+    fake_state_.random_provider()->var_seed()->reset(
+        new uint64_t(4));  // chosen by fair dice roll.
+                           // guaranteed to be random.
+
+    // No device policy loaded by default.
+    fake_state_.device_policy_provider()->var_device_policy_is_loaded()->reset(
+        new bool(false));
+
+    // OOBE is enabled by default.
+    fake_state_.config_provider()->var_is_oobe_enabled()->reset(
+        new bool(true));
+
+    // For the purpose of the tests, this is an official build and OOBE was
+    // completed.
+    fake_state_.system_provider()->var_is_official_build()->reset(
+        new bool(true));
+    fake_state_.system_provider()->var_is_oobe_complete()->reset(
+        new bool(true));
+    fake_state_.system_provider()->var_num_slots()->reset(new unsigned int(2));
+
+    // Connection is wifi, untethered.
+    fake_state_.shill_provider()->var_conn_type()->
+        reset(new ConnectionType(ConnectionType::kWifi));
+    fake_state_.shill_provider()->var_conn_tethering()->
+        reset(new ConnectionTethering(ConnectionTethering::kNotDetected));
+  }
+
+  // Sets up a default device policy that does not impose any restrictions
+  // (HTTP) nor enables any features (P2P).
+  void SetUpDefaultDevicePolicy() {
+    fake_state_.device_policy_provider()->var_device_policy_is_loaded()->reset(
+        new bool(true));
+    fake_state_.device_policy_provider()->var_update_disabled()->reset(
+        new bool(false));
+    fake_state_.device_policy_provider()->
+        var_allowed_connection_types_for_update()->reset(nullptr);
+    fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+        new TimeDelta());
+    fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+        new bool(true));
+    fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+        new bool(false));
+    fake_state_.device_policy_provider()->var_release_channel_delegated()->
+        reset(new bool(true));
+  }
+
+  // Configures the UpdateCheckAllowed policy to return a desired value by
+  // faking the current wall clock time as needed. Restores the default state.
+  // This is used when testing policies that depend on this one.
+  void SetUpdateCheckAllowed(bool allow_check) {
+    Time next_update_check;
+    ExpectPolicyStatus(EvalStatus::kSucceeded,
+                       &ChromeOSPolicy::NextUpdateCheckTime,
+                       &next_update_check);
+    SetUpDefaultState();
+    SetUpDefaultDevicePolicy();
+    Time curr_time = next_update_check;
+    if (allow_check)
+      curr_time += TimeDelta::FromSeconds(1);
+    else
+      curr_time -= TimeDelta::FromSeconds(1);
+    fake_clock_.SetWallclockTime(curr_time);
+  }
+
+  // Returns a default UpdateState structure:
+  UpdateState GetDefaultUpdateState(TimeDelta first_seen_period) {
+    Time first_seen_time = fake_clock_.GetWallclockTime() - first_seen_period;
+    UpdateState update_state = UpdateState();
+
+    // This is a non-interactive check returning a delta payload, seen for the
+    // first time (|first_seen_period| ago). Clearly, there were no failed
+    // attempts so far.
+    update_state.is_interactive = false;
+    update_state.is_delta_payload = false;
+    update_state.first_seen = first_seen_time;
+    update_state.num_checks = 1;
+    update_state.num_failures = 0;
+    update_state.failures_last_updated = Time();  // Needs to be zero.
+    // There's a single HTTP download URL with a maximum of 10 retries.
+    update_state.download_urls = vector<string>{"http://fake/url/"};
+    update_state.download_errors_max = 10;
+    // Download was never attempted.
+    update_state.last_download_url_idx = -1;
+    update_state.last_download_url_num_errors = 0;
+    // There were no download errors.
+    update_state.download_errors = vector<tuple<int, ErrorCode, Time>>();
+    // P2P is not disabled by Omaha.
+    update_state.p2p_downloading_disabled = false;
+    update_state.p2p_sharing_disabled = false;
+    // P2P was not attempted.
+    update_state.p2p_num_attempts = 0;
+    update_state.p2p_first_attempted = Time();
+    // No active backoff period, backoff is not disabled by Omaha.
+    update_state.backoff_expiry = Time();
+    update_state.is_backoff_disabled = false;
+    // There is no active scattering wait period (max 7 days allowed) nor check
+    // threshold (none allowed).
+    update_state.scatter_wait_period = TimeDelta();
+    update_state.scatter_check_threshold = 0;
+    update_state.scatter_wait_period_max = TimeDelta::FromDays(7);
+    update_state.scatter_check_threshold_min = 0;
+    update_state.scatter_check_threshold_max = 0;
+
+    return update_state;
+  }
+
+  // Runs the passed |policy_method| policy and expects it to return the
+  // |expected| return value.
+  template<typename T, typename R, typename... Args>
+  void ExpectPolicyStatus(
+      EvalStatus expected,
+      T policy_method,
+      R* result, Args... args) {
+    string error = "<None>";
+    eval_ctx_->ResetEvaluation();
+    EXPECT_EQ(expected,
+              (policy_.*policy_method)(eval_ctx_.get(), &fake_state_, &error,
+                                       result, args...))
+        << "Returned error: " << error
+        << "\nEvaluation context: " << eval_ctx_->DumpContext();
+  }
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  FakeClock fake_clock_;
+  FakeState fake_state_;
+  scoped_refptr<EvaluationContext> eval_ctx_;
+  ChromeOSPolicy policy_;  // ChromeOSPolicy under test.
+};
+
+TEST_F(UmChromeOSPolicyTest, FirstCheckIsAtMostInitialIntervalAfterStart) {
+  Time next_update_check;
+
+  // Set the last update time so it'll appear as if this is a first update check
+  // in the lifetime of the current updater.
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(fake_clock_.GetWallclockTime() - TimeDelta::FromMinutes(10)));
+
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  EXPECT_LE(fake_clock_.GetWallclockTime(), next_update_check);
+  EXPECT_GE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          ChromeOSPolicy::kTimeoutInitialInterval +
+          ChromeOSPolicy::kTimeoutRegularFuzz / 2),
+      next_update_check);
+}
+
+TEST_F(UmChromeOSPolicyTest, RecurringCheckBaseIntervalAndFuzz) {
+  // Ensure that we're using the correct interval (kPeriodicInterval) and fuzz
+  // (kTimeoutRegularFuzz) as base values for period updates.
+  Time next_update_check;
+
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  EXPECT_LE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          ChromeOSPolicy::kTimeoutPeriodicInterval -
+          ChromeOSPolicy::kTimeoutRegularFuzz / 2),
+      next_update_check);
+  EXPECT_GE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          ChromeOSPolicy::kTimeoutPeriodicInterval +
+          ChromeOSPolicy::kTimeoutRegularFuzz / 2),
+      next_update_check);
+}
+
+TEST_F(UmChromeOSPolicyTest, RecurringCheckBackoffIntervalAndFuzz) {
+  // Ensure that we're properly backing off and fuzzing in the presence of
+  // failed updates attempts.
+  Time next_update_check;
+
+  fake_state_.updater_provider()->var_consecutive_failed_update_checks()->
+      reset(new unsigned int{2});
+
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  int expected_interval = ChromeOSPolicy::kTimeoutPeriodicInterval * 4;
+  EXPECT_LE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          expected_interval - expected_interval / 2),
+      next_update_check);
+  EXPECT_GE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          expected_interval + expected_interval / 2),
+      next_update_check);
+}
+
+TEST_F(UmChromeOSPolicyTest, RecurringCheckServerDictatedPollInterval) {
+  // Policy honors the server provided check poll interval.
+  Time next_update_check;
+
+  const unsigned int kInterval = ChromeOSPolicy::kTimeoutPeriodicInterval * 4;
+  fake_state_.updater_provider()->var_server_dictated_poll_interval()->
+      reset(new unsigned int{kInterval});
+  // We should not be backing off in this case.
+  fake_state_.updater_provider()->var_consecutive_failed_update_checks()->
+      reset(new unsigned int{2});
+
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  EXPECT_LE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          kInterval - kInterval / 2),
+      next_update_check);
+  EXPECT_GE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          kInterval + kInterval / 2),
+      next_update_check);
+}
+
+TEST_F(UmChromeOSPolicyTest, ExponentialBackoffIsCapped) {
+  Time next_update_check;
+
+  fake_state_.updater_provider()->var_consecutive_failed_update_checks()->
+      reset(new unsigned int{100});
+
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  EXPECT_LE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          ChromeOSPolicy::kTimeoutMaxBackoffInterval -
+          ChromeOSPolicy::kTimeoutMaxBackoffInterval / 2),
+      next_update_check);
+  EXPECT_GE(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(
+          ChromeOSPolicy::kTimeoutMaxBackoffInterval +
+          ChromeOSPolicy::kTimeoutMaxBackoffInterval /2),
+      next_update_check);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCheckAllowedWaitsForTheTimeout) {
+  // We get the next update_check timestamp from the policy's private method
+  // and then we check the public method respects that value on the normal
+  // case.
+  Time next_update_check;
+  Time last_checked_time =
+      fake_clock_.GetWallclockTime() + TimeDelta::FromMinutes(1234);
+
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  UpdateCheckParams result;
+
+  // Check that the policy blocks until the next_update_check is reached.
+  SetUpDefaultClock();
+  SetUpDefaultState();
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  fake_clock_.SetWallclockTime(next_update_check - TimeDelta::FromSeconds(1));
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateCheckAllowed, &result);
+
+  SetUpDefaultClock();
+  SetUpDefaultState();
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  fake_clock_.SetWallclockTime(next_update_check + TimeDelta::FromSeconds(1));
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_TRUE(result.updates_enabled);
+  EXPECT_FALSE(result.is_interactive);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCheckAllowedWaitsForOOBE) {
+  // Update checks are deferred until OOBE is completed.
+
+  // Ensure that update is not allowed even if wait period is satisfied.
+  Time next_update_check;
+  Time last_checked_time =
+      fake_clock_.GetWallclockTime() + TimeDelta::FromMinutes(1234);
+
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &ChromeOSPolicy::NextUpdateCheckTime, &next_update_check);
+
+  SetUpDefaultClock();
+  SetUpDefaultState();
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  fake_clock_.SetWallclockTime(next_update_check + TimeDelta::FromSeconds(1));
+  fake_state_.system_provider()->var_is_oobe_complete()->reset(
+      new bool(false));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateCheckAllowed, &result);
+
+  // Now check that it is allowed if OOBE is completed.
+  SetUpDefaultClock();
+  SetUpDefaultState();
+  fake_state_.updater_provider()->var_last_checked_time()->reset(
+      new Time(last_checked_time));
+  fake_clock_.SetWallclockTime(next_update_check + TimeDelta::FromSeconds(1));
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_TRUE(result.updates_enabled);
+  EXPECT_FALSE(result.is_interactive);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCheckAllowedWithAttributes) {
+  // Update check is allowed, response includes attributes for use in the
+  // request.
+  SetUpdateCheckAllowed(true);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_target_version_prefix()->
+      reset(new string("1.2"));
+  fake_state_.device_policy_provider()->var_release_channel_delegated()->
+      reset(new bool(false));
+  fake_state_.device_policy_provider()->var_release_channel()->
+      reset(new string("foo-channel"));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_TRUE(result.updates_enabled);
+  EXPECT_EQ("1.2", result.target_version_prefix);
+  EXPECT_EQ("foo-channel", result.target_channel);
+  EXPECT_FALSE(result.is_interactive);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCheckAllowedUpdatesDisabledForUnofficialBuilds) {
+  // UpdateCheckAllowed should return kAskMeAgainLater if this is an unofficial
+  // build; we don't want periodic update checks on developer images.
+
+  fake_state_.system_provider()->var_is_official_build()->reset(
+      new bool(false));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateCheckAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCheckAllowedUpdatesDisabledForRemovableBootDevice) {
+  // UpdateCheckAllowed should return false (kSucceeded) if the image booted
+  // from a removable device.
+
+  fake_state_.system_provider()->var_num_slots()->reset(new unsigned int(1));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_FALSE(result.updates_enabled);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCheckAllowedUpdatesDisabledByPolicy) {
+  // UpdateCheckAllowed should return kAskMeAgainLater because a device policy
+  // is loaded and prohibits updates.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_update_disabled()->reset(
+      new bool(true));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateCheckAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCheckAllowedForcedUpdateRequestedInteractive) {
+  // UpdateCheckAllowed should return true because a forced update request was
+  // signaled for an interactive update.
+
+  SetUpdateCheckAllowed(true);
+  fake_state_.updater_provider()->var_forced_update_requested()->reset(
+      new UpdateRequestStatus(UpdateRequestStatus::kInteractive));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_TRUE(result.updates_enabled);
+  EXPECT_TRUE(result.is_interactive);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCheckAllowedForcedUpdateRequestedPeriodic) {
+  // UpdateCheckAllowed should return true because a forced update request was
+  // signaled for a periodic check.
+
+  SetUpdateCheckAllowed(true);
+  fake_state_.updater_provider()->var_forced_update_requested()->reset(
+      new UpdateRequestStatus(UpdateRequestStatus::kPeriodic));
+
+  UpdateCheckParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCheckAllowed, &result);
+  EXPECT_TRUE(result.updates_enabled);
+  EXPECT_FALSE(result.is_interactive);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartFailsCheckAllowedError) {
+  // The UpdateCanStart policy fails, not being able to query
+  // UpdateCheckAllowed.
+
+  // Configure the UpdateCheckAllowed policy to fail.
+  fake_state_.updater_provider()->var_updater_started_time()->reset(nullptr);
+
+  // Check that the UpdateCanStart fails.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kFailed,
+                     &Policy::UpdateCanStart, &result, update_state);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartNotAllowedCheckDue) {
+  // The UpdateCanStart policy returns false because we are due for another
+  // update check. Ensure that download related values are still returned.
+
+  SetUpdateCheckAllowed(true);
+
+  // Check that the UpdateCanStart returns false.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCanStart, &result, update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kCheckDue, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_EQ(0, result.download_url_num_errors);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedNoDevicePolicy) {
+  // The UpdateCanStart policy returns true; no device policy is loaded.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_device_policy_is_loaded()->reset(
+      new bool(false));
+
+  // Check that the UpdateCanStart returns true with no further attributes.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCanStart, &result, update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_FALSE(result.p2p_downloading_allowed);
+  EXPECT_FALSE(result.p2p_sharing_allowed);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedBlankPolicy) {
+  // The UpdateCanStart policy returns true; device policy is loaded but imposes
+  // no restrictions on updating.
+
+  SetUpdateCheckAllowed(false);
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateCanStart, &result, update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_FALSE(result.p2p_downloading_allowed);
+  EXPECT_FALSE(result.p2p_sharing_allowed);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedBackoffNewWaitPeriodApplies) {
+  // The UpdateCanStart policy returns false; failures are reported and a new
+  // backoff period is enacted.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kBackoff, result.cannot_start_reason);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_LT(curr_time, result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedBackoffPrevWaitPeriodStillApplies) {
+  // The UpdateCanStart policy returns false; a previously enacted backoff
+  // period still applies.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  update_state.failures_last_updated = curr_time;
+  update_state.backoff_expiry = curr_time + TimeDelta::FromMinutes(3);
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater, &Policy::UpdateCanStart,
+                     &result, update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kBackoff, result.cannot_start_reason);
+  EXPECT_FALSE(result.do_increment_failures);
+  EXPECT_LT(curr_time, result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedBackoffSatisfied) {
+  // The UpdateCanStart policy returns true; a previously enacted backoff period
+  // has elapsed, we're good to go.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  update_state.failures_last_updated = curr_time - TimeDelta::FromSeconds(1);
+  update_state.backoff_expiry = curr_time - TimeDelta::FromSeconds(1);
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart,
+                     &result, update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kUndefined, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+  EXPECT_EQ(Time(), result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedBackoffDisabled) {
+  // The UpdateCanStart policy returns false; failures are reported but backoff
+  // is disabled.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  update_state.is_backoff_disabled = true;
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kUndefined, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_EQ(Time(), result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedNoBackoffInteractive) {
+  // The UpdateCanStart policy returns false; failures are reported but this is
+  // an interactive update check.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  update_state.is_interactive = true;
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kUndefined, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_EQ(Time(), result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedNoBackoffDelta) {
+  // The UpdateCanStart policy returns false; failures are reported but this is
+  // a delta payload.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  update_state.is_delta_payload = true;
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kUndefined, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_EQ(Time(), result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedNoBackoffUnofficialBuild) {
+  // The UpdateCanStart policy returns false; failures are reported but this is
+  // an unofficial build.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+
+  fake_state_.system_provider()->var_is_official_build()->
+      reset(new bool(false));
+
+  // Check that UpdateCanStart returns false and a new backoff expiry is
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kUndefined, result.cannot_start_reason);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_EQ(Time(), result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartFailsScatteringFailed) {
+  // The UpdateCanStart policy fails because the UpdateScattering policy it
+  // depends on fails (unset variable).
+
+  SetUpdateCheckAllowed(false);
+
+  // Override the default seed variable with a null value so that the policy
+  // request would fail.
+  // TODO(garnold) This failure may or may not fail a number
+  // sub-policies/decisions, like scattering and backoff. We'll need a more
+  // deliberate setup to ensure that we're failing what we want to be failing.
+  fake_state_.random_provider()->var_seed()->reset(nullptr);
+
+  // Check that the UpdateCanStart fails.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kFailed,
+                     &Policy::UpdateCanStart, &result, update_state);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedScatteringNewWaitPeriodApplies) {
+  // The UpdateCanStart policy returns false; device policy is loaded and
+  // scattering applies due to an unsatisfied wait period, which was newly
+  // generated.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromMinutes(2)));
+
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+
+  // Check that the UpdateCanStart returns false and a new wait period
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kScattering, result.cannot_start_reason);
+  EXPECT_LT(TimeDelta(), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedScatteringPrevWaitPeriodStillApplies) {
+  // The UpdateCanStart policy returns false w/ kAskMeAgainLater; device policy
+  // is loaded and a previously generated scattering period still applies, none
+  // of the scattering values has changed.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromMinutes(2)));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.scatter_wait_period = TimeDelta::FromSeconds(35);
+
+  // Check that the UpdateCanStart returns false and a new wait period
+  // generated.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater, &Policy::UpdateCanStart,
+                     &result, update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kScattering, result.cannot_start_reason);
+  EXPECT_EQ(TimeDelta::FromSeconds(35), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedScatteringNewCountThresholdApplies) {
+  // The UpdateCanStart policy returns false; device policy is loaded and
+  // scattering applies due to an unsatisfied update check count threshold.
+  //
+  // This ensures a non-zero check threshold, which may or may not be combined
+  // with a non-zero wait period (for which we cannot reliably control).
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromSeconds(1)));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 5;
+
+  // Check that the UpdateCanStart returns false.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kScattering, result.cannot_start_reason);
+  EXPECT_LE(2, result.scatter_check_threshold);
+  EXPECT_GE(5, result.scatter_check_threshold);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartNotAllowedScatteringPrevCountThresholdStillApplies) {
+  // The UpdateCanStart policy returns false; device policy is loaded and
+  // scattering due to a previously generated count threshold still applies.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromSeconds(1)));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.scatter_check_threshold = 3;
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 5;
+
+  // Check that the UpdateCanStart returns false.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kScattering, result.cannot_start_reason);
+  EXPECT_EQ(3, result.scatter_check_threshold);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedScatteringSatisfied) {
+  // The UpdateCanStart policy returns true; device policy is loaded and
+  // scattering is enabled, but both wait period and check threshold are
+  // satisfied.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromSeconds(120)));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(75));
+  update_state.num_checks = 4;
+  update_state.scatter_wait_period = TimeDelta::FromSeconds(60);
+  update_state.scatter_check_threshold = 3;
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 5;
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(TimeDelta(), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedInteractivePreventsScattering) {
+  // The UpdateCanStart policy returns true; device policy is loaded and
+  // scattering would have applied, except that the update check is interactive
+  // and so it is suppressed.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromSeconds(1)));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.is_interactive = true;
+  update_state.scatter_check_threshold = 0;
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 5;
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(TimeDelta(), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedOobePreventsScattering) {
+  // The UpdateCanStart policy returns true; device policy is loaded and
+  // scattering would have applied, except that OOBE was not completed and so it
+  // is suppressed.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromSeconds(1)));
+  fake_state_.system_provider()->var_is_oobe_complete()->reset(new bool(false));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.is_interactive = true;
+  update_state.scatter_check_threshold = 0;
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 5;
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(TimeDelta(), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedWithAttributes) {
+  // The UpdateCanStart policy returns true; device policy permits both HTTP and
+  // P2P updates, as well as a non-empty target channel string.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedWithP2PFromUpdater) {
+  // The UpdateCanStart policy returns true; device policy forbids both HTTP and
+  // P2P updates, but the updater is configured to allow P2P and overrules the
+  // setting.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.updater_provider()->var_p2p_enabled()->reset(new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedP2PDownloadingBlockedDueToOmaha) {
+  // The UpdateCanStart policy returns true; device policy permits HTTP, but
+  // policy blocks P2P downloading because Omaha forbids it.  P2P sharing is
+  // still permitted.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.p2p_downloading_disabled = true;
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_FALSE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedP2PSharingBlockedDueToOmaha) {
+  // The UpdateCanStart policy returns true; device policy permits HTTP, but
+  // policy blocks P2P sharing because Omaha forbids it.  P2P downloading is
+  // still permitted.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.p2p_sharing_disabled = true;
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_FALSE(result.p2p_sharing_allowed);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedP2PDownloadingBlockedDueToNumAttempts) {
+  // The UpdateCanStart policy returns true; device policy permits HTTP but
+  // blocks P2P download, because the max number of P2P downloads have been
+  // attempted. P2P sharing is still permitted.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.p2p_num_attempts = ChromeOSPolicy::kMaxP2PAttempts;
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_FALSE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedP2PDownloadingBlockedDueToAttemptsPeriod) {
+  // The UpdateCanStart policy returns true; device policy permits HTTP but
+  // blocks P2P download, because the max period for attempt to download via P2P
+  // has elapsed. P2P sharing is still permitted.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.p2p_num_attempts = 1;
+  update_state.p2p_first_attempted =
+      fake_clock_.GetWallclockTime() -
+      TimeDelta::FromSeconds(
+          ChromeOSPolicy::kMaxP2PAttemptsPeriodInSeconds + 1);
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_FALSE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedWithHttpUrlForUnofficialBuild) {
+  // The UpdateCanStart policy returns true; device policy forbids both HTTP and
+  // P2P updates, but marking this an unofficial build overrules the HTTP
+  // setting.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(false));
+  fake_state_.system_provider()->var_is_official_build()->
+      reset(new bool(false));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedWithHttpsUrl) {
+  // The UpdateCanStart policy returns true; device policy forbids both HTTP and
+  // P2P updates, but an HTTPS URL is provided and selected for download.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(false));
+
+  // Add an HTTPS URL.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.download_urls.emplace_back("https://secure/url/");
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(1, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedMaxErrorsNotExceeded) {
+  // The UpdateCanStart policy returns true; the first URL has download errors
+  // but does not exceed the maximum allowed number of failures, so it is stilli
+  // usable.
+
+  SetUpdateCheckAllowed(false);
+
+  // Add a second URL; update with this URL attempted and failed enough times to
+  // disqualify the current (first) URL.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.num_checks = 5;
+  update_state.download_urls.emplace_back("http://another/fake/url/");
+  Time t = fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(12);
+  for (int i = 0; i < 5; i++) {
+    update_state.download_errors.emplace_back(
+        0, ErrorCode::kDownloadTransferError, t);
+    t += TimeDelta::FromSeconds(1);
+  }
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(5, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedWithSecondUrlMaxExceeded) {
+  // The UpdateCanStart policy returns true; the first URL exceeded the maximum
+  // allowed number of failures, but a second URL is available.
+
+  SetUpdateCheckAllowed(false);
+
+  // Add a second URL; update with this URL attempted and failed enough times to
+  // disqualify the current (first) URL.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.num_checks = 10;
+  update_state.download_urls.emplace_back("http://another/fake/url/");
+  Time t = fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(12);
+  for (int i = 0; i < 11; i++) {
+    update_state.download_errors.emplace_back(
+        0, ErrorCode::kDownloadTransferError, t);
+    t += TimeDelta::FromSeconds(1);
+  }
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(1, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedWithSecondUrlHardError) {
+  // The UpdateCanStart policy returns true; the first URL fails with a hard
+  // error, but a second URL is available.
+
+  SetUpdateCheckAllowed(false);
+
+  // Add a second URL; update with this URL attempted and failed in a way that
+  // causes it to switch directly to the next URL.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.num_checks = 10;
+  update_state.download_urls.emplace_back("http://another/fake/url/");
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kPayloadHashMismatchError,
+      fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(1));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(1, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedUrlWrapsAround) {
+  // The UpdateCanStart policy returns true; URL search properly wraps around
+  // the last one on the list.
+
+  SetUpdateCheckAllowed(false);
+
+  // Add a second URL; update with this URL attempted and failed in a way that
+  // causes it to switch directly to the next URL. We must disable backoff in
+  // order for it not to interfere.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  update_state.num_checks = 1;
+  update_state.is_backoff_disabled = true;
+  update_state.download_urls.emplace_back("http://another/fake/url/");
+  update_state.download_errors.emplace_back(
+      1, ErrorCode::kPayloadHashMismatchError,
+      fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(1));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartNotAllowedNoUsableUrls) {
+  // The UpdateCanStart policy returns false; there's a single HTTP URL but its
+  // use is forbidden by policy.
+  //
+  // Note: In the case where no usable URLs are found, the policy should not
+  // increment the number of failed attempts! Doing so would result in a
+  // non-idempotent semantics, and does not fall within the intended purpose of
+  // the backoff mechanism anyway.
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(false));
+
+  // Check that the UpdateCanStart returns false.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_FALSE(result.update_can_start);
+  EXPECT_EQ(UpdateCannotStartReason::kCannotDownload,
+            result.cannot_start_reason);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCanStartAllowedNoUsableUrlsButP2PEnabled) {
+  // The UpdateCanStart policy returns true; there's a single HTTP URL but its
+  // use is forbidden by policy, however P2P is enabled. The result indicates
+  // that no URL can be used.
+  //
+  // Note: The number of failed attempts should not increase in this case (see
+  // above test).
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(false));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_GT(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedNoUsableUrlsButEnterpriseEnrolled) {
+  // The UpdateCanStart policy returns true; there's a single HTTP URL but its
+  // use is forbidden by policy, and P2P is unset on the policy, however the
+  // device is enterprise-enrolled so P2P is allowed. The result indicates that
+  // no URL can be used.
+  //
+  // Note: The number of failed attempts should not increase in this case (see
+  // above test).
+
+  SetUpdateCheckAllowed(false);
+
+  // Override specific device policy attributes.
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(nullptr);
+  fake_state_.device_policy_provider()->var_owner()->reset(nullptr);
+  fake_state_.device_policy_provider()->var_http_downloads_enabled()->reset(
+      new bool(false));
+
+  // Check that the UpdateCanStart returns true.
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromMinutes(10));
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_GT(0, result.download_url_idx);
+  EXPECT_TRUE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_FALSE(result.do_increment_failures);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateDownloadAllowedEthernetDefault) {
+  // Ethernet is always allowed.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kEthernet));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateDownloadAllowedWifiDefault) {
+  // Wifi is allowed if not tethered.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kWifi));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCurrentConnectionNotAllowedWifiTetheredDefault) {
+  // Tethered wifi is not allowed by default.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kWifi));
+  fake_state_.shill_provider()->var_conn_tethering()->
+      reset(new ConnectionTethering(ConnectionTethering::kConfirmed));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateDownloadAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateDownloadAllowedWifiTetheredPolicyOverride) {
+  // Tethered wifi can be allowed by policy.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kWifi));
+  fake_state_.shill_provider()->var_conn_tethering()->
+      reset(new ConnectionTethering(ConnectionTethering::kConfirmed));
+  set<ConnectionType> allowed_connections;
+  allowed_connections.insert(ConnectionType::kCellular);
+  fake_state_.device_policy_provider()->
+      var_allowed_connection_types_for_update()->
+      reset(new set<ConnectionType>(allowed_connections));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateDownloadAllowedWimaxDefault) {
+  // Wimax is always allowed.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kWifi));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCurrentConnectionNotAllowedBluetoothDefault) {
+  // Bluetooth is never allowed.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kBluetooth));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateDownloadAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCurrentConnectionNotAllowedBluetoothPolicyCannotOverride) {
+  // Bluetooth cannot be allowed even by policy.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kBluetooth));
+  set<ConnectionType> allowed_connections;
+  allowed_connections.insert(ConnectionType::kBluetooth);
+  fake_state_.device_policy_provider()->
+      var_allowed_connection_types_for_update()->
+      reset(new set<ConnectionType>(allowed_connections));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateDownloadAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest, UpdateCurrentConnectionNotAllowedCellularDefault) {
+  // Cellular is not allowed by default.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kCellular));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater,
+                     &Policy::UpdateDownloadAllowed, &result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateDownloadAllowedCellularPolicyOverride) {
+  // Update over cellular can be enabled by policy.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kCellular));
+  set<ConnectionType> allowed_connections;
+  allowed_connections.insert(ConnectionType::kCellular);
+  fake_state_.device_policy_provider()->
+      var_allowed_connection_types_for_update()->
+      reset(new set<ConnectionType>(allowed_connections));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateDownloadAllowedCellularUserOverride) {
+  // Update over cellular can be enabled by user settings, but only if policy
+  // is present and does not determine allowed connections.
+
+  fake_state_.shill_provider()->var_conn_type()->
+      reset(new ConnectionType(ConnectionType::kCellular));
+  set<ConnectionType> allowed_connections;
+  allowed_connections.insert(ConnectionType::kCellular);
+  fake_state_.updater_provider()->var_cellular_enabled()->
+      reset(new bool(true));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded,
+                     &Policy::UpdateDownloadAllowed, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedScatteringSupressedDueToP2P) {
+  // The UpdateCanStart policy returns true; scattering should have applied, but
+  // P2P download is allowed. Scattering values are nonetheless returned, and so
+  // are download URL values, albeit the latter are not allowed to be used.
+
+  SetUpdateCheckAllowed(false);
+  fake_state_.device_policy_provider()->var_scatter_factor()->reset(
+      new TimeDelta(TimeDelta::FromMinutes(2)));
+  fake_state_.updater_provider()->var_p2p_enabled()->reset(new bool(true));
+
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(1));
+  update_state.scatter_wait_period = TimeDelta::FromSeconds(35);
+
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart,
+                     &result, update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_FALSE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_FALSE(result.do_increment_failures);
+  EXPECT_EQ(TimeDelta::FromSeconds(35), result.scatter_wait_period);
+  EXPECT_EQ(0, result.scatter_check_threshold);
+}
+
+TEST_F(UmChromeOSPolicyTest,
+       UpdateCanStartAllowedBackoffSupressedDueToP2P) {
+  // The UpdateCanStart policy returns true; backoff should have applied, but
+  // P2P download is allowed. Backoff values are nonetheless returned, and so
+  // are download URL values, albeit the latter are not allowed to be used.
+
+  SetUpdateCheckAllowed(false);
+
+  const Time curr_time = fake_clock_.GetWallclockTime();
+  UpdateState update_state = GetDefaultUpdateState(TimeDelta::FromSeconds(10));
+  update_state.download_errors_max = 1;
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(8));
+  update_state.download_errors.emplace_back(
+      0, ErrorCode::kDownloadTransferError,
+      curr_time - TimeDelta::FromSeconds(2));
+  fake_state_.updater_provider()->var_p2p_enabled()->reset(new bool(true));
+
+  UpdateDownloadParams result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::UpdateCanStart, &result,
+                     update_state);
+  EXPECT_TRUE(result.update_can_start);
+  EXPECT_EQ(0, result.download_url_idx);
+  EXPECT_FALSE(result.download_url_allowed);
+  EXPECT_EQ(0, result.download_url_num_errors);
+  EXPECT_TRUE(result.p2p_downloading_allowed);
+  EXPECT_TRUE(result.p2p_sharing_allowed);
+  EXPECT_TRUE(result.do_increment_failures);
+  EXPECT_LT(curr_time, result.backoff_expiry);
+}
+
+TEST_F(UmChromeOSPolicyTest, P2PEnabledNotAllowed) {
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::P2PEnabled, &result);
+  EXPECT_FALSE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, P2PEnabledAllowedByDevicePolicy) {
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(
+      new bool(true));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::P2PEnabled, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, P2PEnabledAllowedByUpdater) {
+  fake_state_.updater_provider()->var_p2p_enabled()->reset(new bool(true));
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::P2PEnabled, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, P2PEnabledAllowedDeviceEnterpriseEnrolled) {
+  fake_state_.device_policy_provider()->var_au_p2p_enabled()->reset(nullptr);
+  fake_state_.device_policy_provider()->var_owner()->reset(nullptr);
+
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kSucceeded, &Policy::P2PEnabled, &result);
+  EXPECT_TRUE(result);
+}
+
+TEST_F(UmChromeOSPolicyTest, P2PEnabledChangedBlocks) {
+  bool result;
+  ExpectPolicyStatus(EvalStatus::kAskMeAgainLater, &Policy::P2PEnabledChanged,
+                     &result, false);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/config_provider.h b/update_manager/config_provider.h
new file mode 100644
index 0000000..36d57a7
--- /dev/null
+++ b/update_manager/config_provider.h
@@ -0,0 +1,43 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_CONFIG_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_CONFIG_PROVIDER_H_
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Provider for const system configurations. This provider reads the
+// configuration from a file on /etc.
+class ConfigProvider : public Provider {
+ public:
+  // Returns a variable stating whether the out of the box experience (OOBE) is
+  // enabled on this device. A value of false means that the device doesn't have
+  // an OOBE workflow.
+  virtual Variable<bool>* var_is_oobe_enabled() = 0;
+
+ protected:
+  ConfigProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ConfigProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_CONFIG_PROVIDER_H_
diff --git a/update_manager/default_policy.cc b/update_manager/default_policy.cc
new file mode 100644
index 0000000..9a5ce7e
--- /dev/null
+++ b/update_manager/default_policy.cc
@@ -0,0 +1,107 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/default_policy.h"
+
+namespace {
+
+// A fixed minimum interval between consecutive allowed update checks. This
+// needs to be long enough to prevent busywork and/or DDoS attacks on Omaha, but
+// at the same time short enough to allow the machine to update itself
+// reasonably soon.
+const int kCheckIntervalInSeconds = 15 * 60;
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+DefaultPolicy::DefaultPolicy(chromeos_update_engine::ClockInterface* clock)
+    : clock_(clock), aux_state_(new DefaultPolicyState()) {}
+
+EvalStatus DefaultPolicy::UpdateCheckAllowed(
+    EvaluationContext* ec, State* state, std::string* error,
+    UpdateCheckParams* result) const {
+  result->updates_enabled = true;
+  result->target_channel.clear();
+  result->target_version_prefix.clear();
+  result->is_interactive = false;
+
+  // Ensure that the minimum interval is set. If there's no clock, this defaults
+  // to always allowing the update.
+  if (!aux_state_->IsLastCheckAllowedTimeSet() ||
+      ec->IsMonotonicTimeGreaterThan(
+          aux_state_->last_check_allowed_time() +
+          base::TimeDelta::FromSeconds(kCheckIntervalInSeconds))) {
+    if (clock_)
+      aux_state_->set_last_check_allowed_time(clock_->GetMonotonicTime());
+    return EvalStatus::kSucceeded;
+  }
+
+  return EvalStatus::kAskMeAgainLater;
+}
+
+EvalStatus DefaultPolicy::UpdateCanStart(
+    EvaluationContext* ec,
+    State* state,
+    std::string* error,
+    UpdateDownloadParams* result,
+    const UpdateState update_state) const {
+  result->update_can_start = true;
+  result->cannot_start_reason = UpdateCannotStartReason::kUndefined;
+  result->download_url_idx = 0;
+  result->download_url_allowed = true;
+  result->download_url_num_errors = 0;
+  result->p2p_downloading_allowed = false;
+  result->p2p_sharing_allowed = false;
+  result->do_increment_failures = false;
+  result->backoff_expiry = base::Time();
+  result->scatter_wait_period = base::TimeDelta();
+  result->scatter_check_threshold = 0;
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus DefaultPolicy::UpdateDownloadAllowed(
+    EvaluationContext* ec,
+    State* state,
+    std::string* error,
+    bool* result) const {
+  *result = true;
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus DefaultPolicy::P2PEnabled(
+    EvaluationContext* ec,
+    State* state,
+    std::string* error,
+    bool* result) const {
+  *result = false;
+  return EvalStatus::kSucceeded;
+}
+
+EvalStatus DefaultPolicy::P2PEnabledChanged(
+    EvaluationContext* ec,
+    State* state,
+    std::string* error,
+    bool* result,
+    bool prev_result) const {
+  // This policy will always prohibit P2P, so this is signaling to the caller
+  // that the decision is final (because the current value is the same as the
+  // previous one) and there's no need to issue another call.
+  *result = false;
+  return EvalStatus::kSucceeded;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/default_policy.h b/update_manager/default_policy.h
new file mode 100644
index 0000000..3f41178
--- /dev/null
+++ b/update_manager/default_policy.h
@@ -0,0 +1,105 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_DEFAULT_POLICY_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_DEFAULT_POLICY_H_
+
+#include <memory>
+#include <string>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/update_manager/policy.h"
+
+namespace chromeos_update_manager {
+
+// Auxiliary state class for DefaultPolicy evaluations.
+//
+// IMPORTANT: The use of a state object in policies is generally forbidden, as
+// it was a design decision to keep policy calls side-effect free. We make an
+// exception here to ensure that DefaultPolicy indeed serves as a safe (and
+// secure) fallback option. This practice should be avoided when imlpementing
+// other policies.
+class DefaultPolicyState {
+ public:
+  DefaultPolicyState() {}
+
+  bool IsLastCheckAllowedTimeSet() const {
+    return last_check_allowed_time_ != base::Time::Max();
+  }
+
+  // Sets/returns the point time on the monotonic time scale when the latest
+  // check allowed was recorded.
+  void set_last_check_allowed_time(base::Time timestamp) {
+    last_check_allowed_time_ = timestamp;
+  }
+  base::Time last_check_allowed_time() const {
+    return last_check_allowed_time_;
+  }
+
+ private:
+  base::Time last_check_allowed_time_ = base::Time::Max();
+};
+
+// The DefaultPolicy is a safe Policy implementation that doesn't fail. The
+// values returned by this policy are safe default in case of failure of the
+// actual policy being used by the UpdateManager.
+class DefaultPolicy : public Policy {
+ public:
+  explicit DefaultPolicy(chromeos_update_engine::ClockInterface* clock);
+  DefaultPolicy() : DefaultPolicy(nullptr) {}
+  ~DefaultPolicy() override {}
+
+  // Policy overrides.
+  EvalStatus UpdateCheckAllowed(
+      EvaluationContext* ec, State* state, std::string* error,
+      UpdateCheckParams* result) const override;
+
+  EvalStatus UpdateCanStart(
+      EvaluationContext* ec, State* state, std::string* error,
+      UpdateDownloadParams* result,
+      UpdateState update_state) const override;
+
+  EvalStatus UpdateDownloadAllowed(
+      EvaluationContext* ec, State* state, std::string* error,
+      bool* result) const override;
+
+  EvalStatus P2PEnabled(
+      EvaluationContext* ec, State* state, std::string* error,
+      bool* result) const override;
+
+  EvalStatus P2PEnabledChanged(
+      EvaluationContext* ec, State* state, std::string* error,
+      bool* result, bool prev_result) const override;
+
+ protected:
+  // Policy override.
+  std::string PolicyName() const override { return "DefaultPolicy"; }
+
+ private:
+  // A clock interface.
+  chromeos_update_engine::ClockInterface* clock_;
+
+  // An auxiliary state object.
+  std::unique_ptr<DefaultPolicyState> aux_state_;
+
+  DISALLOW_COPY_AND_ASSIGN(DefaultPolicy);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_DEFAULT_POLICY_H_
diff --git a/update_manager/device_policy_provider.h b/update_manager/device_policy_provider.h
new file mode 100644
index 0000000..f75d470
--- /dev/null
+++ b/update_manager/device_policy_provider.h
@@ -0,0 +1,75 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_DEVICE_POLICY_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_DEVICE_POLICY_PROVIDER_H_
+
+#include <set>
+#include <string>
+
+#include <base/time/time.h>
+#include <policy/libpolicy.h>
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/shill_provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Provides access to the current DevicePolicy.
+class DevicePolicyProvider : public Provider {
+ public:
+  ~DevicePolicyProvider() override {}
+
+  // Variable stating whether the DevicePolicy was loaded.
+  virtual Variable<bool>* var_device_policy_is_loaded() = 0;
+
+  // Variables mapping the information received on the DevicePolicy protobuf.
+  virtual Variable<std::string>* var_release_channel() = 0;
+
+  virtual Variable<bool>* var_release_channel_delegated() = 0;
+
+  virtual Variable<bool>* var_update_disabled() = 0;
+
+  virtual Variable<std::string>* var_target_version_prefix() = 0;
+
+  // Returns a non-negative scatter interval used for updates.
+  virtual Variable<base::TimeDelta>* var_scatter_factor() = 0;
+
+  // Variable returning the set of connection types allowed for updates. The
+  // identifiers returned are consistent with the ones returned by the
+  // ShillProvider.
+  virtual Variable<std::set<ConnectionType>>*
+      var_allowed_connection_types_for_update() = 0;
+
+  // Variable stating the name of the device owner. For enterprise enrolled
+  // devices, this will be an empty string.
+  virtual Variable<std::string>* var_owner() = 0;
+
+  virtual Variable<bool>* var_http_downloads_enabled() = 0;
+
+  virtual Variable<bool>* var_au_p2p_enabled() = 0;
+
+ protected:
+  DevicePolicyProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(DevicePolicyProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_DEVICE_POLICY_PROVIDER_H_
diff --git a/update_manager/evaluation_context-inl.h b/update_manager/evaluation_context-inl.h
new file mode 100644
index 0000000..937adf4
--- /dev/null
+++ b/update_manager/evaluation_context-inl.h
@@ -0,0 +1,55 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_INL_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_INL_H_
+
+#include <string>
+
+#include <base/logging.h>
+
+namespace chromeos_update_manager {
+
+template<typename T>
+const T* EvaluationContext::GetValue(Variable<T>* var) {
+  if (var == nullptr) {
+    LOG(ERROR) << "GetValue received an uninitialized variable.";
+    return nullptr;
+  }
+
+  // Search for the value on the cache first.
+  ValueCacheMap::iterator it = value_cache_.find(var);
+  if (it != value_cache_.end())
+    return reinterpret_cast<const T*>(it->second.value());
+
+  // Get the value from the variable if not found on the cache.
+  std::string errmsg;
+  const T* result = var->GetValue(RemainingTime(evaluation_monotonic_deadline_),
+                                  &errmsg);
+  if (result == nullptr) {
+    LOG(WARNING) << "Error reading Variable " << var->GetName() << ": \""
+        << errmsg << "\"";
+  }
+  // Cache the value for the next time. The map of CachedValues keeps the
+  // ownership of the pointer until the map is destroyed.
+  value_cache_.emplace(
+    static_cast<BaseVariable*>(var), BoxedValue(result));
+  return result;
+}
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_INL_H_
diff --git a/update_manager/evaluation_context.cc b/update_manager/evaluation_context.cc
new file mode 100644
index 0000000..03ac0b7
--- /dev/null
+++ b/update_manager/evaluation_context.cc
@@ -0,0 +1,252 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/evaluation_context.h"
+
+#include <algorithm>
+#include <memory>
+#include <string>
+
+#include <base/bind.h>
+#include <base/json/json_writer.h>
+#include <base/location.h>
+#include <base/strings/string_util.h>
+#include <base/values.h>
+
+#include "update_engine/common/utils.h"
+
+using base::Callback;
+using base::Closure;
+using base::Time;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using chromeos_update_engine::ClockInterface;
+using std::string;
+using std::unique_ptr;
+
+namespace {
+
+// Returns whether |curr_time| surpassed |ref_time|; if not, also checks whether
+// |ref_time| is sooner than the current value of |*reeval_time|, in which case
+// the latter is updated to the former.
+bool IsTimeGreaterThanHelper(Time ref_time, Time curr_time,
+                             Time* reeval_time) {
+  if (curr_time > ref_time)
+    return true;
+  // Remember the nearest reference we've checked against in this evaluation.
+  if (*reeval_time > ref_time)
+    *reeval_time = ref_time;
+  return false;
+}
+
+// If |expires| never happens (maximal value), returns the maximal interval;
+// otherwise, returns the difference between |expires| and |curr|.
+TimeDelta GetTimeout(Time curr, Time expires) {
+  if (expires.is_max())
+    return TimeDelta::Max();
+  return expires - curr;
+}
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+EvaluationContext::EvaluationContext(
+    ClockInterface* clock,
+    TimeDelta evaluation_timeout,
+    TimeDelta expiration_timeout,
+    unique_ptr<Callback<void(EvaluationContext*)>> unregister_cb)
+    : clock_(clock),
+      evaluation_timeout_(evaluation_timeout),
+      expiration_timeout_(expiration_timeout),
+      unregister_cb_(std::move(unregister_cb)),
+      weak_ptr_factory_(this) {
+  ResetEvaluation();
+  ResetExpiration();
+}
+
+EvaluationContext::~EvaluationContext() {
+  RemoveObserversAndTimeout();
+  if (unregister_cb_.get())
+    unregister_cb_->Run(this);
+}
+
+unique_ptr<Closure> EvaluationContext::RemoveObserversAndTimeout() {
+  for (auto& it : value_cache_) {
+    if (it.first->GetMode() == kVariableModeAsync)
+      it.first->RemoveObserver(this);
+  }
+  MessageLoop::current()->CancelTask(timeout_event_);
+  timeout_event_ = MessageLoop::kTaskIdNull;
+
+  return unique_ptr<Closure>(callback_.release());
+}
+
+TimeDelta EvaluationContext::RemainingTime(Time monotonic_deadline) const {
+  if (monotonic_deadline.is_max())
+    return TimeDelta::Max();
+  TimeDelta remaining = monotonic_deadline - clock_->GetMonotonicTime();
+  return std::max(remaining, TimeDelta());
+}
+
+Time EvaluationContext::MonotonicDeadline(TimeDelta timeout) {
+  return (timeout.is_max() ? Time::Max() :
+          clock_->GetMonotonicTime() + timeout);
+}
+
+void EvaluationContext::ValueChanged(BaseVariable* var) {
+  DLOG(INFO) << "ValueChanged() called for variable " << var->GetName();
+  OnValueChangedOrTimeout();
+}
+
+void EvaluationContext::OnTimeout() {
+  DLOG(INFO) << "OnTimeout() called due to "
+             << (timeout_marks_expiration_ ? "expiration" : "poll interval");
+  timeout_event_ = MessageLoop::kTaskIdNull;
+  is_expired_ = timeout_marks_expiration_;
+  OnValueChangedOrTimeout();
+}
+
+void EvaluationContext::OnValueChangedOrTimeout() {
+  // Copy the callback handle locally, allowing it to be reassigned.
+  unique_ptr<Closure> callback = RemoveObserversAndTimeout();
+
+  if (callback.get())
+    callback->Run();
+}
+
+bool EvaluationContext::IsWallclockTimeGreaterThan(Time timestamp) {
+  return IsTimeGreaterThanHelper(timestamp, evaluation_start_wallclock_,
+                                 &reevaluation_time_wallclock_);
+}
+
+bool EvaluationContext::IsMonotonicTimeGreaterThan(Time timestamp) {
+  return IsTimeGreaterThanHelper(timestamp, evaluation_start_monotonic_,
+                                 &reevaluation_time_monotonic_);
+}
+
+void EvaluationContext::ResetEvaluation() {
+  evaluation_start_wallclock_ = clock_->GetWallclockTime();
+  evaluation_start_monotonic_ = clock_->GetMonotonicTime();
+  reevaluation_time_wallclock_ = Time::Max();
+  reevaluation_time_monotonic_ = Time::Max();
+  evaluation_monotonic_deadline_ = MonotonicDeadline(evaluation_timeout_);
+
+  // Remove the cached values of non-const variables
+  for (auto it = value_cache_.begin(); it != value_cache_.end(); ) {
+    if (it->first->GetMode() == kVariableModeConst) {
+      ++it;
+    } else {
+      it = value_cache_.erase(it);
+    }
+  }
+}
+
+void EvaluationContext::ResetExpiration() {
+  expiration_monotonic_deadline_ = MonotonicDeadline(expiration_timeout_);
+  is_expired_ = false;
+}
+
+bool EvaluationContext::RunOnValueChangeOrTimeout(Closure callback) {
+  // Check that the method was not called more than once.
+  if (callback_.get()) {
+    LOG(ERROR) << "RunOnValueChangeOrTimeout called more than once.";
+    return false;
+  }
+
+  // Check that the context did not yet expire.
+  if (is_expired()) {
+    LOG(ERROR) << "RunOnValueChangeOrTimeout called on an expired context.";
+    return false;
+  }
+
+  // Handle reevaluation due to a Is{Wallclock,Monotonic}TimeGreaterThan(). We
+  // choose the smaller of the differences between evaluation start time and
+  // reevaluation time among the wallclock and monotonic scales.
+  TimeDelta timeout = std::min(
+      GetTimeout(evaluation_start_wallclock_, reevaluation_time_wallclock_),
+      GetTimeout(evaluation_start_monotonic_, reevaluation_time_monotonic_));
+
+  // Handle reevaluation due to async or poll variables.
+  bool waiting_for_value_change = false;
+  for (auto& it : value_cache_) {
+    switch (it.first->GetMode()) {
+      case kVariableModeAsync:
+        DLOG(INFO) << "Waiting for value on " << it.first->GetName();
+        it.first->AddObserver(this);
+        waiting_for_value_change = true;
+        break;
+      case kVariableModePoll:
+        timeout = std::min(timeout, it.first->GetPollInterval());
+        break;
+      case kVariableModeConst:
+        // Ignored.
+        break;
+    }
+  }
+
+  // Check if the re-evaluation is actually being scheduled. If there are no
+  // events waited for, this function should return false.
+  if (!waiting_for_value_change && timeout.is_max())
+    return false;
+
+  // Ensure that we take into account the expiration timeout.
+  TimeDelta expiration = RemainingTime(expiration_monotonic_deadline_);
+  timeout_marks_expiration_ = expiration < timeout;
+  if (timeout_marks_expiration_)
+    timeout = expiration;
+
+  // Store the reevaluation callback.
+  callback_.reset(new Closure(callback));
+
+  // Schedule a timeout event, if one is set.
+  if (!timeout.is_max()) {
+    DLOG(INFO) << "Waiting for timeout in "
+               << chromeos_update_engine::utils::FormatTimeDelta(timeout);
+    timeout_event_ = MessageLoop::current()->PostDelayedTask(
+        FROM_HERE,
+        base::Bind(&EvaluationContext::OnTimeout,
+                   weak_ptr_factory_.GetWeakPtr()),
+        timeout);
+  }
+
+  return true;
+}
+
+string EvaluationContext::DumpContext() const {
+  base::DictionaryValue* variables = new base::DictionaryValue();
+  for (auto& it : value_cache_) {
+    variables->SetString(it.first->GetName(), it.second.ToString());
+  }
+
+  base::DictionaryValue value;
+  value.Set("variables", variables);  // Adopts |variables|.
+  value.SetString(
+      "evaluation_start_wallclock",
+      chromeos_update_engine::utils::ToString(evaluation_start_wallclock_));
+  value.SetString(
+      "evaluation_start_monotonic",
+      chromeos_update_engine::utils::ToString(evaluation_start_monotonic_));
+
+  string json_str;
+  base::JSONWriter::WriteWithOptions(
+      value, base::JSONWriter::OPTIONS_PRETTY_PRINT, &json_str);
+  base::TrimWhitespaceASCII(json_str, base::TRIM_TRAILING, &json_str);
+
+  return json_str;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/evaluation_context.h b/update_manager/evaluation_context.h
new file mode 100644
index 0000000..df5816a
--- /dev/null
+++ b/update_manager/evaluation_context.h
@@ -0,0 +1,221 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_H_
+
+#include <map>
+#include <memory>
+#include <string>
+
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/memory/ref_counted.h>
+#include <base/memory/weak_ptr.h>
+#include <base/time/time.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/update_manager/boxed_value.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// The EvaluationContext class is the interface between a policy implementation
+// and the state. The EvaluationContext tracks the variables used by a policy
+// request and caches the returned values, owning those cached values.
+// The same EvaluationContext should be re-used for all the evaluations of the
+// same policy request (an AsyncPolicyRequest might involve several
+// re-evaluations). Each evaluation of the EvaluationContext is run at a given
+// point in time, which is used as a reference for the evaluation timeout and
+// the time based queries of the policy, such as
+// Is{Wallclock,Monotonic}TimeGreaterThan().
+//
+// Example:
+//
+//   scoped_refptr<EvaluationContext> ec = new EvaluationContext(...);
+//
+//   ...
+//   // The following call to ResetEvaluation() is optional. Use it to reset the
+//   // evaluation time if the EvaluationContext isn't used right after its
+//   // construction.
+//   ec->ResetEvaluation();
+//   EvalStatus status = policy->SomeMethod(ec, state, &result, args...);
+//
+//   ...
+//   // Run a closure when any of the used async variables changes its value or
+//   // the timeout for re-query the values happens again.
+//   ec->RunOnValueChangeOrTimeout(closure);
+//   // If the provided |closure| wants to re-evaluate the policy, it should
+//   // call ec->ResetEvaluation() to start a new evaluation.
+//
+class EvaluationContext : public base::RefCounted<EvaluationContext>,
+                          private BaseVariable::ObserverInterface {
+ public:
+  EvaluationContext(
+      chromeos_update_engine::ClockInterface* clock,
+      base::TimeDelta evaluation_timeout,
+      base::TimeDelta expiration_timeout,
+      std::unique_ptr<base::Callback<void(EvaluationContext*)>> unregister_cb);
+  EvaluationContext(chromeos_update_engine::ClockInterface* clock,
+                    base::TimeDelta evaluation_timeout)
+      : EvaluationContext(
+          clock, evaluation_timeout, base::TimeDelta::Max(),
+          std::unique_ptr<base::Callback<void(EvaluationContext*)>>()) {}
+  ~EvaluationContext();
+
+  // Returns a pointer to the value returned by the passed variable |var|. The
+  // EvaluationContext instance keeps the ownership of the returned object. The
+  // returned object is valid during the life of the evaluation, even if the
+  // passed Variable changes it.
+  //
+  // In case of error, a null value is returned.
+  template<typename T>
+  const T* GetValue(Variable<T>* var);
+
+  // Returns whether the evaluation time has surpassed |timestamp|, on either
+  // the ClockInterface::GetWallclockTime() or
+  // ClockInterface::GetMonotonicTime() scales, respectively.
+  bool IsWallclockTimeGreaterThan(base::Time timestamp);
+  bool IsMonotonicTimeGreaterThan(base::Time timestamp);
+
+  // Returns whether the evaluation context has expired.
+  bool is_expired() const { return is_expired_; }
+
+  // TODO(deymo): Move the following methods to an interface only visible by the
+  // UpdateManager class and not the policy implementations.
+
+  // Resets the EvaluationContext to its initial state removing all the
+  // non-const cached variables and re-setting the evaluation time. This should
+  // be called right before any new evaluation starts.
+  void ResetEvaluation();
+
+  // Clears the expiration status of the EvaluationContext and resets its
+  // expiration timeout based on |expiration_timeout_|. This should be called if
+  // expiration occurred, prior to re-evaluating the policy.
+  void ResetExpiration();
+
+  // Schedules the passed |callback| closure to be called when a cached
+  // variable changes its value, a polling interval passes, or the context
+  // expiration occurs. If none of these events can happen, for example if
+  // there's no cached variable, this method returns false.
+  //
+  // Right before the passed closure is called the EvaluationContext is
+  // reseted, removing all the non-const cached values.
+  bool RunOnValueChangeOrTimeout(base::Closure callback);
+
+  // Returns a textual representation of the evaluation context,
+  // including the variables and their values. This is intended only
+  // to help with debugging and the format may change in the future.
+  std::string DumpContext() const;
+
+  // Removes all the Observers callbacks and timeout events scheduled by
+  // RunOnValueChangeOrTimeout(). Also releases and returns the closure
+  // associated with these events. This method is idempotent.
+  std::unique_ptr<base::Closure> RemoveObserversAndTimeout();
+
+ private:
+  friend class UmEvaluationContextTest;
+
+  // BaseVariable::ObserverInterface override.
+  void ValueChanged(BaseVariable* var) override;
+
+  // Called from the main loop when a scheduled timeout has passed.
+  void OnTimeout();
+
+  // Removes the observers from the used Variables and cancels the timeout,
+  // then executes the scheduled callback.
+  void OnValueChangedOrTimeout();
+
+  // If |monotonic_deadline| is not Time::Max(), returns the remaining time
+  // until it is reached, or zero if it has passed. Otherwise, returns
+  // TimeDelta::Max().
+  base::TimeDelta RemainingTime(base::Time monotonic_deadline) const;
+
+  // Returns a monotonic clock timestamp at which |timeout| will have elapsed
+  // since the current time.
+  base::Time MonotonicDeadline(base::TimeDelta timeout);
+
+  // A map to hold the cached values for every variable.
+  typedef std::map<BaseVariable*, BoxedValue> ValueCacheMap;
+
+  // The cached values of the called Variables.
+  ValueCacheMap value_cache_;
+
+  // A callback used for triggering re-evaluation upon a value change or poll
+  // timeout, or notifying about the evaluation context expiration. It is up to
+  // the caller to determine whether or not expiration occurred via
+  // is_expired().
+  std::unique_ptr<base::Closure> callback_;
+
+  // The TaskId returned by the message loop identifying the timeout callback.
+  // Used for canceling the timeout callback.
+  brillo::MessageLoop::TaskId timeout_event_ =
+      brillo::MessageLoop::kTaskIdNull;
+
+  // Whether a timeout event firing marks the expiration of the evaluation
+  // context.
+  bool timeout_marks_expiration_;
+
+  // Whether the evaluation context has indeed expired.
+  bool is_expired_ = false;
+
+  // Pointer to the mockable clock interface;
+  chromeos_update_engine::ClockInterface* const clock_;
+
+  // The timestamps when the evaluation of this EvaluationContext started,
+  // corresponding to ClockInterface::GetWallclockTime() and
+  // ClockInterface::GetMonotonicTime(), respectively. These values are reset
+  // every time ResetEvaluation() is called.
+  base::Time evaluation_start_wallclock_;
+  base::Time evaluation_start_monotonic_;
+
+  // The timestamps when a reevaluation should be triggered due to various
+  // expected value changes, corresponding to ClockInterface::GetWallclockTime()
+  // and ClockInterface::GetMonotonicTIme(), respectively. These timestamps are
+  // greater or equal to corresponding |evaluation_start_{wallclock,monotonic}_|
+  // counterparts since they are in the future; however, they may be smaller
+  // than the current corresponding times during the course of evaluation.
+  base::Time reevaluation_time_wallclock_;
+  base::Time reevaluation_time_monotonic_;
+
+  // The timeout of an evaluation.
+  const base::TimeDelta evaluation_timeout_;
+
+  // The timestamp in the ClockInterface::GetMonotonicTime() scale at which the
+  // current evaluation should finish.
+  base::Time evaluation_monotonic_deadline_;
+
+  // The expiration timeout of the evaluation context.
+  const base::TimeDelta expiration_timeout_;
+
+  // The monotonic clock deadline at which expiration occurs.
+  base::Time expiration_monotonic_deadline_;
+
+  // A callback for unregistering the context upon destruction.
+  std::unique_ptr<base::Callback<void(EvaluationContext*)>> unregister_cb_;
+
+  base::WeakPtrFactory<EvaluationContext> weak_ptr_factory_;
+
+  DISALLOW_COPY_AND_ASSIGN(EvaluationContext);
+};
+
+}  // namespace chromeos_update_manager
+
+// Include the implementation of the template methods.
+#include "update_engine/update_manager/evaluation_context-inl.h"
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_EVALUATION_CONTEXT_H_
diff --git a/update_manager/evaluation_context_unittest.cc b/update_manager/evaluation_context_unittest.cc
new file mode 100644
index 0000000..1e61db7
--- /dev/null
+++ b/update_manager/evaluation_context_unittest.cc
@@ -0,0 +1,489 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/evaluation_context.h"
+
+#include <memory>
+#include <string>
+
+#include <base/bind.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/generic_variables.h"
+#include "update_engine/update_manager/mock_variable.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Bind;
+using base::Closure;
+using base::Time;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using brillo::MessageLoopRunMaxIterations;
+using brillo::MessageLoopRunUntil;
+using chromeos_update_engine::FakeClock;
+using std::string;
+using std::unique_ptr;
+using testing::Return;
+using testing::StrictMock;
+using testing::_;
+
+namespace chromeos_update_manager {
+
+namespace {
+
+void DoNothing() {}
+
+// Sets the value of the passed pointer to true.
+void SetTrue(bool* value) {
+  *value = true;
+}
+
+bool GetBoolean(bool* value) {
+  return *value;
+}
+
+template<typename T>
+void ReadVar(scoped_refptr<EvaluationContext> ec, Variable<T>* var) {
+  ec->GetValue(var);
+}
+
+// Runs |evaluation|; if the value pointed by |count_p| is greater than zero,
+// decrement it and schedule a reevaluation; otherwise, writes true to |done_p|.
+void EvaluateRepeatedly(Closure evaluation, scoped_refptr<EvaluationContext> ec,
+                        int* count_p, bool* done_p) {
+  evaluation.Run();
+
+  // Schedule reevaluation if needed.
+  if (*count_p > 0) {
+    Closure closure = Bind(EvaluateRepeatedly, evaluation, ec, count_p, done_p);
+    ASSERT_TRUE(ec->RunOnValueChangeOrTimeout(closure))
+        << "Failed to schedule reevaluation, count_p=" << *count_p;
+    (*count_p)--;
+  } else {
+    *done_p = true;
+  }
+}
+
+}  // namespace
+
+class UmEvaluationContextTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    // Apr 22, 2009 19:25:00 UTC (this is a random reference point).
+    fake_clock_.SetMonotonicTime(Time::FromTimeT(1240428300));
+    // Mar 2, 2006 1:23:45 UTC.
+    fake_clock_.SetWallclockTime(Time::FromTimeT(1141262625));
+    eval_ctx_ = new EvaluationContext(
+        &fake_clock_, default_timeout_, default_timeout_,
+        unique_ptr<base::Callback<void(EvaluationContext*)>>(nullptr));
+  }
+
+  void TearDown() override {
+    // Ensure that the evaluation context did not leak and is actually being
+    // destroyed.
+    if (eval_ctx_) {
+      base::WeakPtr<EvaluationContext> eval_ctx_weak_alias =
+          eval_ctx_->weak_ptr_factory_.GetWeakPtr();
+      ASSERT_NE(nullptr, eval_ctx_weak_alias.get());
+      eval_ctx_ = nullptr;
+      EXPECT_EQ(nullptr, eval_ctx_weak_alias.get())
+          << "The evaluation context was not destroyed! This is likely a bug "
+             "in how the test was written, look for leaking handles to the EC, "
+             "possibly through closure objects.";
+    }
+
+    // Check that the evaluation context removed all the observers.
+    EXPECT_TRUE(fake_int_var_.observer_list_.empty());
+    EXPECT_TRUE(fake_async_var_.observer_list_.empty());
+    EXPECT_TRUE(fake_const_var_.observer_list_.empty());
+    EXPECT_TRUE(fake_poll_var_.observer_list_.empty());
+
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  TimeDelta default_timeout_ = TimeDelta::FromSeconds(5);
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  FakeClock fake_clock_;
+  scoped_refptr<EvaluationContext> eval_ctx_;
+
+  // FakeVariables used for testing the EvaluationContext. These are required
+  // here to prevent them from going away *before* the EvaluationContext under
+  // test does, which keeps a reference to them.
+  FakeVariable<bool> fail_var_ = {"fail_var", kVariableModePoll};
+  FakeVariable<int> fake_int_var_ = {"fake_int", kVariableModePoll};
+  FakeVariable<string> fake_async_var_ = {"fake_async", kVariableModeAsync};
+  FakeVariable<string> fake_const_var_ = {"fake_const", kVariableModeConst};
+  FakeVariable<string> fake_poll_var_ = {"fake_poll",
+                                         TimeDelta::FromSeconds(1)};
+  StrictMock<MockVariable<string>> mock_var_async_ {
+    "mock_var_async", kVariableModeAsync};
+  StrictMock<MockVariable<string>> mock_var_poll_ {
+    "mock_var_poll", kVariableModePoll};
+};
+
+TEST_F(UmEvaluationContextTest, GetValueFails) {
+  // FakeVariable is initialized as returning null.
+  EXPECT_EQ(nullptr, eval_ctx_->GetValue(&fake_int_var_));
+}
+
+TEST_F(UmEvaluationContextTest, GetValueFailsWithInvalidVar) {
+  EXPECT_EQ(nullptr, eval_ctx_->GetValue(static_cast<Variable<int>*>(nullptr)));
+}
+
+TEST_F(UmEvaluationContextTest, GetValueReturns) {
+  const int* p_fake_int;
+
+  fake_int_var_.reset(new int(42));
+  p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+  ASSERT_NE(nullptr, p_fake_int);
+  EXPECT_EQ(42, *p_fake_int);
+}
+
+TEST_F(UmEvaluationContextTest, GetValueCached) {
+  const int* p_fake_int;
+
+  fake_int_var_.reset(new int(42));
+  p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+
+  // Check that if the variable changes, the EvaluationContext keeps returning
+  // the cached value.
+  fake_int_var_.reset(new int(5));
+
+  p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+  ASSERT_NE(nullptr, p_fake_int);
+  EXPECT_EQ(42, *p_fake_int);
+}
+
+TEST_F(UmEvaluationContextTest, GetValueCachesNull) {
+  const int* p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+  EXPECT_EQ(nullptr, p_fake_int);
+
+  fake_int_var_.reset(new int(42));
+  // A second attempt to read the variable should not work because this
+  // EvaluationContext already got a null value.
+  p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+  EXPECT_EQ(nullptr, p_fake_int);
+}
+
+TEST_F(UmEvaluationContextTest, GetValueMixedTypes) {
+  const int* p_fake_int;
+  const string* p_fake_string;
+
+  fake_int_var_.reset(new int(42));
+  fake_poll_var_.reset(new string("Hello world!"));
+  // Check that the EvaluationContext can handle multiple Variable types. This
+  // is mostly a compile-time check due to the template nature of this method.
+  p_fake_int = eval_ctx_->GetValue(&fake_int_var_);
+  p_fake_string = eval_ctx_->GetValue(&fake_poll_var_);
+
+  ASSERT_NE(nullptr, p_fake_int);
+  EXPECT_EQ(42, *p_fake_int);
+
+  ASSERT_NE(nullptr, p_fake_string);
+  EXPECT_EQ("Hello world!", *p_fake_string);
+}
+
+// Test that we don't schedule an event if there's no variable to wait for.
+TEST_F(UmEvaluationContextTest, RunOnValueChangeOrTimeoutWithoutVariables) {
+  fake_const_var_.reset(new string("Hello world!"));
+  EXPECT_EQ(*eval_ctx_->GetValue(&fake_const_var_), "Hello world!");
+
+  EXPECT_FALSE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+// Test that reevaluation occurs when an async variable it depends on changes.
+TEST_F(UmEvaluationContextTest, RunOnValueChangeOrTimeoutWithVariables) {
+  fake_async_var_.reset(new string("Async value"));
+  eval_ctx_->GetValue(&fake_async_var_);
+
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  // Check that the scheduled callback isn't run until we signal a ValueChaged.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_FALSE(value);
+
+  fake_async_var_.NotifyValueChanged();
+  EXPECT_FALSE(value);
+  // Ensure that the scheduled callback isn't run until we are back on the main
+  // loop.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_TRUE(value);
+}
+
+// Test that we don't re-schedule the events if we are attending one.
+TEST_F(UmEvaluationContextTest, RunOnValueChangeOrTimeoutCalledTwice) {
+  fake_async_var_.reset(new string("Async value"));
+  eval_ctx_->GetValue(&fake_async_var_);
+
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  EXPECT_FALSE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+
+  // The scheduled event should still work.
+  fake_async_var_.NotifyValueChanged();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_TRUE(value);
+}
+
+// Test that reevaluation occurs when a polling timeout fires.
+TEST_F(UmEvaluationContextTest, RunOnValueChangeOrTimeoutRunsFromTimeout) {
+  fake_poll_var_.reset(new string("Polled value"));
+  eval_ctx_->GetValue(&fake_poll_var_);
+
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  // Check that the scheduled callback isn't run until the timeout occurs.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 10);
+  EXPECT_FALSE(value);
+  MessageLoopRunUntil(MessageLoop::current(),
+                      TimeDelta::FromSeconds(10),
+                      Bind(&GetBoolean, &value));
+  EXPECT_TRUE(value);
+}
+
+// Test that callback is called when evaluation context expires, and that it
+// cannot be used again unless the expiration deadline is reset.
+TEST_F(UmEvaluationContextTest, RunOnValueChangeOrTimeoutExpires) {
+  fake_async_var_.reset(new string("Async value"));
+  eval_ctx_->GetValue(&fake_async_var_);
+
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  // Check that the scheduled callback isn't run until the timeout occurs.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 10);
+  EXPECT_FALSE(value);
+  MessageLoopRunUntil(MessageLoop::current(),
+                      TimeDelta::FromSeconds(10),
+                      Bind(&GetBoolean, &value));
+  EXPECT_TRUE(value);
+
+  // Ensure that we cannot reschedule an evaluation.
+  EXPECT_FALSE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+
+  // Ensure that we can reschedule an evaluation after resetting expiration.
+  eval_ctx_->ResetExpiration();
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+// Test that we clear the events when destroying the EvaluationContext.
+TEST_F(UmEvaluationContextTest, RemoveObserversAndTimeoutTest) {
+  fake_async_var_.reset(new string("Async value"));
+  eval_ctx_->GetValue(&fake_async_var_);
+
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  eval_ctx_ = nullptr;
+
+  // This should not trigger the callback since the EvaluationContext waiting
+  // for it is gone, and it should have remove all its observers.
+  fake_async_var_.NotifyValueChanged();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_FALSE(value);
+}
+
+// Scheduling two reevaluations from the callback should succeed.
+TEST_F(UmEvaluationContextTest,
+       RunOnValueChangeOrTimeoutReevaluatesRepeatedly) {
+  fake_poll_var_.reset(new string("Polled value"));
+  Closure evaluation = Bind(ReadVar<string>, eval_ctx_, &fake_poll_var_);
+  int num_reevaluations = 2;
+  bool done = false;
+
+  // Run the evaluation once.
+  evaluation.Run();
+
+  // Schedule repeated reevaluations.
+  Closure closure = Bind(EvaluateRepeatedly, evaluation, eval_ctx_,
+                         &num_reevaluations, &done);
+  ASSERT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(closure));
+  MessageLoopRunUntil(MessageLoop::current(),
+                      TimeDelta::FromSeconds(10),
+                      Bind(&GetBoolean, &done));
+  EXPECT_EQ(0, num_reevaluations);
+}
+
+// Test that we can delete the EvaluationContext while having pending events.
+TEST_F(UmEvaluationContextTest, ObjectDeletedWithPendingEventsTest) {
+  fake_async_var_.reset(new string("Async value"));
+  fake_poll_var_.reset(new string("Polled value"));
+  eval_ctx_->GetValue(&fake_async_var_);
+  eval_ctx_->GetValue(&fake_poll_var_);
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+  // TearDown() checks for leaked observers on this async_variable, which means
+  // that our object is still alive after removing its reference.
+}
+
+// Test that timed events fired after removal of the EvaluationContext don't
+// crash.
+TEST_F(UmEvaluationContextTest, TimeoutEventAfterDeleteTest) {
+  FakeVariable<string> fake_short_poll_var = {"fake_short_poll",
+                                              TimeDelta::FromSeconds(1)};
+  fake_short_poll_var.reset(new string("Polled value"));
+  eval_ctx_->GetValue(&fake_short_poll_var);
+  bool value = false;
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&SetTrue, &value)));
+  // Remove the last reference to the EvaluationContext and run the loop for
+  // 10 seconds to give time to the main loop to trigger the timeout Event (of 1
+  // second). Our callback should not be called because the EvaluationContext
+  // was removed before the timeout event is attended.
+  eval_ctx_ = nullptr;
+  MessageLoopRunUntil(MessageLoop::current(),
+                      TimeDelta::FromSeconds(10),
+                      Bind(&GetBoolean, &value));
+  EXPECT_FALSE(value);
+}
+
+TEST_F(UmEvaluationContextTest, DefaultTimeout) {
+  // Test that the evaluation timeout calculation uses the default timeout on
+  // setup.
+  EXPECT_CALL(mock_var_async_, GetValue(default_timeout_, _))
+      .WillOnce(Return(nullptr));
+  EXPECT_EQ(nullptr, eval_ctx_->GetValue(&mock_var_async_));
+}
+
+TEST_F(UmEvaluationContextTest, TimeoutUpdatesWithMonotonicTime) {
+  fake_clock_.SetMonotonicTime(
+      fake_clock_.GetMonotonicTime() + TimeDelta::FromSeconds(1));
+
+  TimeDelta timeout = default_timeout_ - TimeDelta::FromSeconds(1);
+
+  EXPECT_CALL(mock_var_async_, GetValue(timeout, _))
+      .WillOnce(Return(nullptr));
+  EXPECT_EQ(nullptr, eval_ctx_->GetValue(&mock_var_async_));
+}
+
+TEST_F(UmEvaluationContextTest, ResetEvaluationResetsTimesWallclock) {
+  Time cur_time = fake_clock_.GetWallclockTime();
+  // Advance the time on the clock but don't call ResetEvaluation yet.
+  fake_clock_.SetWallclockTime(cur_time + TimeDelta::FromSeconds(4));
+
+  EXPECT_TRUE(eval_ctx_->IsWallclockTimeGreaterThan(
+          cur_time - TimeDelta::FromSeconds(1)));
+  EXPECT_FALSE(eval_ctx_->IsWallclockTimeGreaterThan(cur_time));
+  EXPECT_FALSE(eval_ctx_->IsWallclockTimeGreaterThan(
+          cur_time + TimeDelta::FromSeconds(1)));
+  // Call ResetEvaluation now, which should use the new evaluation time.
+  eval_ctx_->ResetEvaluation();
+
+  cur_time = fake_clock_.GetWallclockTime();
+  EXPECT_TRUE(eval_ctx_->IsWallclockTimeGreaterThan(
+          cur_time - TimeDelta::FromSeconds(1)));
+  EXPECT_FALSE(eval_ctx_->IsWallclockTimeGreaterThan(cur_time));
+  EXPECT_FALSE(eval_ctx_->IsWallclockTimeGreaterThan(
+          cur_time + TimeDelta::FromSeconds(1)));
+}
+
+TEST_F(UmEvaluationContextTest, ResetEvaluationResetsTimesMonotonic) {
+  Time cur_time = fake_clock_.GetMonotonicTime();
+  // Advance the time on the clock but don't call ResetEvaluation yet.
+  fake_clock_.SetMonotonicTime(cur_time + TimeDelta::FromSeconds(4));
+
+  EXPECT_TRUE(eval_ctx_->IsMonotonicTimeGreaterThan(
+          cur_time - TimeDelta::FromSeconds(1)));
+  EXPECT_FALSE(eval_ctx_->IsMonotonicTimeGreaterThan(cur_time));
+  EXPECT_FALSE(eval_ctx_->IsMonotonicTimeGreaterThan(
+          cur_time + TimeDelta::FromSeconds(1)));
+  // Call ResetEvaluation now, which should use the new evaluation time.
+  eval_ctx_->ResetEvaluation();
+
+  cur_time = fake_clock_.GetMonotonicTime();
+  EXPECT_TRUE(eval_ctx_->IsMonotonicTimeGreaterThan(
+          cur_time - TimeDelta::FromSeconds(1)));
+  EXPECT_FALSE(eval_ctx_->IsMonotonicTimeGreaterThan(cur_time));
+  EXPECT_FALSE(eval_ctx_->IsMonotonicTimeGreaterThan(
+          cur_time + TimeDelta::FromSeconds(1)));
+}
+
+TEST_F(UmEvaluationContextTest,
+       IsWallclockTimeGreaterThanSignalsTriggerReevaluation) {
+  EXPECT_FALSE(eval_ctx_->IsWallclockTimeGreaterThan(
+      fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(1)));
+
+  // The "false" from IsWallclockTimeGreaterThan means that's not that timestamp
+  // yet, so this should schedule a callback for when that happens.
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+TEST_F(UmEvaluationContextTest,
+       IsMonotonicTimeGreaterThanSignalsTriggerReevaluation) {
+  EXPECT_FALSE(eval_ctx_->IsMonotonicTimeGreaterThan(
+      fake_clock_.GetMonotonicTime() + TimeDelta::FromSeconds(1)));
+
+  // The "false" from IsMonotonicTimeGreaterThan means that's not that timestamp
+  // yet, so this should schedule a callback for when that happens.
+  EXPECT_TRUE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+TEST_F(UmEvaluationContextTest,
+       IsWallclockTimeGreaterThanDoesntRecordPastTimestamps) {
+  // IsWallclockTimeGreaterThan() should ignore timestamps on the past for
+  // reevaluation.
+  EXPECT_TRUE(eval_ctx_->IsWallclockTimeGreaterThan(
+      fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(20)));
+  EXPECT_TRUE(eval_ctx_->IsWallclockTimeGreaterThan(
+      fake_clock_.GetWallclockTime() - TimeDelta::FromSeconds(1)));
+
+  // Callback should not be scheduled.
+  EXPECT_FALSE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+TEST_F(UmEvaluationContextTest,
+       IsMonotonicTimeGreaterThanDoesntRecordPastTimestamps) {
+  // IsMonotonicTimeGreaterThan() should ignore timestamps on the past for
+  // reevaluation.
+  EXPECT_TRUE(eval_ctx_->IsMonotonicTimeGreaterThan(
+      fake_clock_.GetMonotonicTime() - TimeDelta::FromSeconds(20)));
+  EXPECT_TRUE(eval_ctx_->IsMonotonicTimeGreaterThan(
+      fake_clock_.GetMonotonicTime() - TimeDelta::FromSeconds(1)));
+
+  // Callback should not be scheduled.
+  EXPECT_FALSE(eval_ctx_->RunOnValueChangeOrTimeout(Bind(&DoNothing)));
+}
+
+TEST_F(UmEvaluationContextTest, DumpContext) {
+  // |fail_var_| yield "(no value)" since it is unset.
+  eval_ctx_->GetValue(&fail_var_);
+
+  // Check that this is included.
+  fake_int_var_.reset(new int(42));
+  eval_ctx_->GetValue(&fake_int_var_);
+
+  // Check that double-quotes are escaped properly.
+  fake_poll_var_.reset(new string("Hello \"world\"!"));
+  eval_ctx_->GetValue(&fake_poll_var_);
+
+  // Note that the variables are printed in alphabetical order. Also
+  // see UmEvaluationContextText::SetUp() where the values used for
+  // |evaluation_start_{monotonic,wallclock| are set.
+  EXPECT_EQ("{\n"
+            "   \"evaluation_start_monotonic\": \"4/22/2009 19:25:00 GMT\",\n"
+            "   \"evaluation_start_wallclock\": \"3/2/2006 1:23:45 GMT\",\n"
+            "   \"variables\": {\n"
+            "      \"fail_var\": \"(no value)\",\n"
+            "      \"fake_int\": \"42\",\n"
+            "      \"fake_poll\": \"Hello \\\"world\\\"!\"\n"
+            "   }\n"
+            "}",
+            eval_ctx_->DumpContext());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/fake_config_provider.h b/update_manager/fake_config_provider.h
new file mode 100644
index 0000000..6a324df
--- /dev/null
+++ b/update_manager/fake_config_provider.h
@@ -0,0 +1,43 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_CONFIG_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_CONFIG_PROVIDER_H_
+
+#include "update_engine/update_manager/config_provider.h"
+#include "update_engine/update_manager/fake_variable.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the ConfigProvider base class.
+class FakeConfigProvider : public ConfigProvider {
+ public:
+  FakeConfigProvider() {}
+
+  FakeVariable<bool>* var_is_oobe_enabled() override {
+    return &var_is_oobe_enabled_;
+  }
+
+ private:
+  FakeVariable<bool> var_is_oobe_enabled_{  // NOLINT(whitespace/braces)
+      "is_oobe_enabled", kVariableModeConst};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeConfigProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_CONFIG_PROVIDER_H_
diff --git a/update_manager/fake_device_policy_provider.h b/update_manager/fake_device_policy_provider.h
new file mode 100644
index 0000000..ad15c99
--- /dev/null
+++ b/update_manager/fake_device_policy_provider.h
@@ -0,0 +1,100 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_DEVICE_POLICY_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_DEVICE_POLICY_PROVIDER_H_
+
+#include <set>
+#include <string>
+
+#include "update_engine/update_manager/device_policy_provider.h"
+#include "update_engine/update_manager/fake_variable.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the DevicePolicyProvider base class.
+class FakeDevicePolicyProvider : public DevicePolicyProvider {
+ public:
+  FakeDevicePolicyProvider() {}
+
+  FakeVariable<bool>* var_device_policy_is_loaded() override {
+    return &var_device_policy_is_loaded_;
+  }
+
+  FakeVariable<std::string>* var_release_channel() override {
+    return &var_release_channel_;
+  }
+
+  FakeVariable<bool>* var_release_channel_delegated() override {
+    return &var_release_channel_delegated_;
+  }
+
+  FakeVariable<bool>* var_update_disabled() override {
+    return &var_update_disabled_;
+  }
+
+  FakeVariable<std::string>* var_target_version_prefix() override {
+    return &var_target_version_prefix_;
+  }
+
+  FakeVariable<base::TimeDelta>* var_scatter_factor() override {
+    return &var_scatter_factor_;
+  }
+
+  FakeVariable<std::set<ConnectionType>>*
+      var_allowed_connection_types_for_update() override {
+    return &var_allowed_connection_types_for_update_;
+  }
+
+  FakeVariable<std::string>* var_owner() override {
+    return &var_owner_;
+  }
+
+  FakeVariable<bool>* var_http_downloads_enabled() override {
+    return &var_http_downloads_enabled_;
+  }
+
+  FakeVariable<bool>* var_au_p2p_enabled() override {
+    return &var_au_p2p_enabled_;
+  }
+
+ private:
+  FakeVariable<bool> var_device_policy_is_loaded_{
+      "policy_is_loaded", kVariableModePoll};
+  FakeVariable<std::string> var_release_channel_{
+      "release_channel", kVariableModePoll};
+  FakeVariable<bool> var_release_channel_delegated_{
+      "release_channel_delegated", kVariableModePoll};
+  FakeVariable<bool> var_update_disabled_{
+      "update_disabled", kVariableModePoll};
+  FakeVariable<std::string> var_target_version_prefix_{
+      "target_version_prefix", kVariableModePoll};
+  FakeVariable<base::TimeDelta> var_scatter_factor_{
+      "scatter_factor", kVariableModePoll};
+  FakeVariable<std::set<ConnectionType>>
+      var_allowed_connection_types_for_update_{
+          "allowed_connection_types_for_update", kVariableModePoll};
+  FakeVariable<std::string> var_owner_{"owner", kVariableModePoll};
+  FakeVariable<bool> var_http_downloads_enabled_{
+      "http_downloads_enabled", kVariableModePoll};
+  FakeVariable<bool> var_au_p2p_enabled_{"au_p2p_enabled", kVariableModePoll};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeDevicePolicyProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_DEVICE_POLICY_PROVIDER_H_
diff --git a/update_manager/fake_random_provider.h b/update_manager/fake_random_provider.h
new file mode 100644
index 0000000..643a194
--- /dev/null
+++ b/update_manager/fake_random_provider.h
@@ -0,0 +1,40 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_RANDOM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_RANDOM_PROVIDER_H_
+
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/random_provider.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the RandomProvider base class.
+class FakeRandomProvider : public RandomProvider {
+ public:
+  FakeRandomProvider() {}
+
+  FakeVariable<uint64_t>* var_seed() override { return &var_seed_; }
+
+ private:
+  FakeVariable<uint64_t> var_seed_{"seed", kVariableModePoll};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeRandomProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_RANDOM_PROVIDER_H_
diff --git a/update_manager/fake_shill_provider.h b/update_manager/fake_shill_provider.h
new file mode 100644
index 0000000..b68e858
--- /dev/null
+++ b/update_manager/fake_shill_provider.h
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SHILL_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SHILL_PROVIDER_H_
+
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/shill_provider.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the ShillProvider base class.
+class FakeShillProvider : public ShillProvider {
+ public:
+  FakeShillProvider() {}
+
+  FakeVariable<bool>* var_is_connected() override {
+    return &var_is_connected_;
+  }
+
+  FakeVariable<ConnectionType>* var_conn_type() override {
+    return &var_conn_type_;
+  }
+
+  FakeVariable<ConnectionTethering>*
+      var_conn_tethering() override {
+    return &var_conn_tethering_;
+  }
+
+  FakeVariable<base::Time>* var_conn_last_changed() override {
+    return &var_conn_last_changed_;
+  }
+
+ private:
+  FakeVariable<bool> var_is_connected_{"is_connected", kVariableModePoll};
+  FakeVariable<ConnectionType> var_conn_type_{"conn_type", kVariableModePoll};
+  FakeVariable<ConnectionTethering> var_conn_tethering_{
+      "conn_tethering", kVariableModePoll};
+  FakeVariable<base::Time> var_conn_last_changed_{
+      "conn_last_changed", kVariableModePoll};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeShillProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SHILL_PROVIDER_H_
diff --git a/update_manager/fake_state.h b/update_manager/fake_state.h
new file mode 100644
index 0000000..fd7a88c
--- /dev/null
+++ b/update_manager/fake_state.h
@@ -0,0 +1,91 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_STATE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_STATE_H_
+
+#include "update_engine/update_manager/fake_config_provider.h"
+#include "update_engine/update_manager/fake_device_policy_provider.h"
+#include "update_engine/update_manager/fake_random_provider.h"
+#include "update_engine/update_manager/fake_shill_provider.h"
+#include "update_engine/update_manager/fake_system_provider.h"
+#include "update_engine/update_manager/fake_time_provider.h"
+#include "update_engine/update_manager/fake_updater_provider.h"
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+// A fake State class that creates fake providers for all the providers.
+// This fake can be used in unit testing of Policy subclasses. To fake out the
+// value a variable is exposing, just call FakeVariable<T>::SetValue() on the
+// variable you fake out. For example:
+//
+//   FakeState fake_state_;
+//   fake_state_.random_provider_->var_seed()->SetValue(new uint64_t(12345));
+//
+// You can call SetValue more than once and the FakeVariable will take care of
+// the memory, but only the last value will remain.
+class FakeState : public State {
+ public:
+  // Creates and initializes the FakeState using fake providers.
+  FakeState() {}
+
+  ~FakeState() override {}
+
+  // Downcasted getters to access the fake instances during testing.
+  FakeConfigProvider* config_provider() override {
+    return &config_provider_;
+  }
+
+  FakeDevicePolicyProvider* device_policy_provider() override {
+    return &device_policy_provider_;
+  }
+
+  FakeRandomProvider* random_provider() override {
+    return &random_provider_;
+  }
+
+  FakeShillProvider* shill_provider() override {
+    return &shill_provider_;
+  }
+
+  FakeSystemProvider* system_provider() override {
+    return &system_provider_;
+  }
+
+  FakeTimeProvider* time_provider() override {
+    return &time_provider_;
+  }
+
+  FakeUpdaterProvider* updater_provider() override {
+    return &updater_provider_;
+  }
+
+ private:
+  FakeConfigProvider config_provider_;
+  FakeDevicePolicyProvider device_policy_provider_;
+  FakeRandomProvider random_provider_;
+  FakeShillProvider shill_provider_;
+  FakeSystemProvider system_provider_;
+  FakeTimeProvider time_provider_;
+  FakeUpdaterProvider updater_provider_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeState);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_STATE_H_
diff --git a/update_manager/fake_system_provider.h b/update_manager/fake_system_provider.h
new file mode 100644
index 0000000..6036198
--- /dev/null
+++ b/update_manager/fake_system_provider.h
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SYSTEM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SYSTEM_PROVIDER_H_
+
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/system_provider.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the SystemProvider base class.
+class FakeSystemProvider : public SystemProvider {
+ public:
+  FakeSystemProvider() {}
+
+  FakeVariable<bool>* var_is_normal_boot_mode() override {
+    return &var_is_normal_boot_mode_;
+  }
+
+  FakeVariable<bool>* var_is_official_build() override {
+    return &var_is_official_build_;
+  }
+
+  FakeVariable<bool>* var_is_oobe_complete() override {
+    return &var_is_oobe_complete_;
+  }
+
+  FakeVariable<unsigned int>* var_num_slots() override {
+    return &var_num_slots_;
+  }
+
+ private:
+  FakeVariable<bool> var_is_normal_boot_mode_{  // NOLINT(whitespace/braces)
+    "is_normal_boot_mode", kVariableModeConst};
+  FakeVariable<bool> var_is_official_build_{  // NOLINT(whitespace/braces)
+    "is_official_build", kVariableModeConst};
+  FakeVariable<bool> var_is_oobe_complete_{  // NOLINT(whitespace/braces)
+    "is_oobe_complete", kVariableModePoll};
+  FakeVariable<unsigned int> var_num_slots_{"num_slots", kVariableModePoll};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeSystemProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_SYSTEM_PROVIDER_H_
diff --git a/update_manager/fake_time_provider.h b/update_manager/fake_time_provider.h
new file mode 100644
index 0000000..2aea2e7
--- /dev/null
+++ b/update_manager/fake_time_provider.h
@@ -0,0 +1,42 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_TIME_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_TIME_PROVIDER_H_
+
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/time_provider.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the TimeProvider base class.
+class FakeTimeProvider : public TimeProvider {
+ public:
+  FakeTimeProvider() {}
+
+  FakeVariable<base::Time>* var_curr_date() override { return &var_curr_date_; }
+  FakeVariable<int>* var_curr_hour() override { return &var_curr_hour_; }
+
+ private:
+  FakeVariable<base::Time> var_curr_date_{"curr_date", kVariableModePoll};
+  FakeVariable<int> var_curr_hour_{"curr_hour", kVariableModePoll};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeTimeProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_TIME_PROVIDER_H_
diff --git a/update_manager/fake_update_manager.h b/update_manager/fake_update_manager.h
new file mode 100644
index 0000000..2ea00b6
--- /dev/null
+++ b/update_manager/fake_update_manager.h
@@ -0,0 +1,49 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATE_MANAGER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATE_MANAGER_H_
+
+#include "update_engine/update_manager/update_manager.h"
+
+#include "update_engine/update_manager/default_policy.h"
+#include "update_engine/update_manager/fake_state.h"
+
+namespace chromeos_update_manager {
+
+class FakeUpdateManager : public UpdateManager {
+ public:
+  explicit FakeUpdateManager(chromeos_update_engine::ClockInterface* clock)
+      : UpdateManager(clock, base::TimeDelta::FromSeconds(5),
+                      base::TimeDelta::FromHours(1), new FakeState()) {
+    // The FakeUpdateManager uses a DefaultPolicy.
+    set_policy(new DefaultPolicy(clock));
+  }
+
+  // UpdateManager overrides.
+  using UpdateManager::set_policy;
+
+  FakeState* state() {
+    return reinterpret_cast<FakeState*>(UpdateManager::state());
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(FakeUpdateManager);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATE_MANAGER_H_
diff --git a/update_manager/fake_updater_provider.h b/update_manager/fake_updater_provider.h
new file mode 100644
index 0000000..44389f4
--- /dev/null
+++ b/update_manager/fake_updater_provider.h
@@ -0,0 +1,130 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATER_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATER_PROVIDER_H_
+
+#include <string>
+
+#include "update_engine/update_manager/fake_variable.h"
+#include "update_engine/update_manager/updater_provider.h"
+
+namespace chromeos_update_manager {
+
+// Fake implementation of the UpdaterProvider base class.
+class FakeUpdaterProvider : public UpdaterProvider {
+ public:
+  FakeUpdaterProvider() {}
+
+  FakeVariable<base::Time>* var_updater_started_time() override {
+    return &var_updater_started_time_;
+  }
+
+  FakeVariable<base::Time>* var_last_checked_time() override {
+    return &var_last_checked_time_;
+  }
+
+  FakeVariable<base::Time>* var_update_completed_time() override {
+    return &var_update_completed_time_;
+  }
+
+  FakeVariable<double>* var_progress() override {
+    return &var_progress_;
+  }
+
+  FakeVariable<Stage>* var_stage() override {
+    return &var_stage_;
+  }
+
+  FakeVariable<std::string>* var_new_version() override {
+    return &var_new_version_;
+  }
+
+  FakeVariable<int64_t>* var_payload_size() override {
+    return &var_payload_size_;
+  }
+
+  FakeVariable<std::string>* var_curr_channel() override {
+    return &var_curr_channel_;
+  }
+
+  FakeVariable<std::string>* var_new_channel() override {
+    return &var_new_channel_;
+  }
+
+  FakeVariable<bool>* var_p2p_enabled() override {
+    return &var_p2p_enabled_;
+  }
+
+  FakeVariable<bool>* var_cellular_enabled() override {
+    return &var_cellular_enabled_;
+  }
+
+  FakeVariable<unsigned int>* var_consecutive_failed_update_checks() override {
+    return &var_consecutive_failed_update_checks_;
+  }
+
+  FakeVariable<unsigned int>* var_server_dictated_poll_interval() override {
+    return &var_server_dictated_poll_interval_;
+  }
+
+  FakeVariable<UpdateRequestStatus>* var_forced_update_requested() override {
+    return &var_forced_update_requested_;
+  }
+
+ private:
+  FakeVariable<base::Time>
+      var_updater_started_time_{  // NOLINT(whitespace/braces)
+    "updater_started_time", kVariableModePoll};
+  FakeVariable<base::Time> var_last_checked_time_{  // NOLINT(whitespace/braces)
+    "last_checked_time", kVariableModePoll};
+  FakeVariable<base::Time>
+      var_update_completed_time_{  // NOLINT(whitespace/braces)
+    "update_completed_time", kVariableModePoll};
+  FakeVariable<double> var_progress_{  // NOLINT(whitespace/braces)
+    "progress", kVariableModePoll};
+  FakeVariable<Stage> var_stage_{  // NOLINT(whitespace/braces)
+    "stage", kVariableModePoll};
+  FakeVariable<std::string> var_new_version_{  // NOLINT(whitespace/braces)
+    "new_version", kVariableModePoll};
+  FakeVariable<int64_t> var_payload_size_{  // NOLINT(whitespace/braces)
+    "payload_size", kVariableModePoll};
+  FakeVariable<std::string> var_curr_channel_{  // NOLINT(whitespace/braces)
+    "curr_channel", kVariableModePoll};
+  FakeVariable<std::string> var_new_channel_{  // NOLINT(whitespace/braces)
+    "new_channel", kVariableModePoll};
+  FakeVariable<bool> var_p2p_enabled_{// NOLINT(whitespace/braces)
+                                      "p2p_enabled",
+                                      kVariableModeAsync};
+  FakeVariable<bool> var_cellular_enabled_{// NOLINT(whitespace/braces)
+                                           "cellular_enabled",
+                                           kVariableModeAsync};
+  FakeVariable<unsigned int>
+      var_consecutive_failed_update_checks_{  // NOLINT(whitespace/braces)
+    "consecutive_failed_update_checks", kVariableModePoll};
+  FakeVariable<unsigned int>
+      var_server_dictated_poll_interval_{  // NOLINT(whitespace/braces)
+    "server_dictated_poll_interval", kVariableModePoll};
+  FakeVariable<UpdateRequestStatus>
+      var_forced_update_requested_{  // NOLINT(whitespace/braces)
+    "forced_update_requested", kVariableModeAsync};
+
+  DISALLOW_COPY_AND_ASSIGN(FakeUpdaterProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_UPDATER_PROVIDER_H_
diff --git a/update_manager/fake_variable.h b/update_manager/fake_variable.h
new file mode 100644
index 0000000..2f8e079
--- /dev/null
+++ b/update_manager/fake_variable.h
@@ -0,0 +1,74 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_FAKE_VARIABLE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_FAKE_VARIABLE_H_
+
+#include <memory>
+#include <string>
+
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// A fake typed variable to use while testing policy implementations. The
+// variable can be instructed to return any object of its type.
+template<typename T>
+class FakeVariable : public Variable<T> {
+ public:
+  FakeVariable(const std::string& name, VariableMode mode)
+      : Variable<T>(name, mode) {}
+  FakeVariable(const std::string& name, base::TimeDelta poll_interval)
+      : Variable<T>(name, poll_interval) {}
+  ~FakeVariable() override {}
+
+  // Sets the next value of this variable to the passed |p_value| pointer. Once
+  // returned by GetValue(), the pointer is released and has to be set again.
+  // A value of null means that the GetValue() call will fail and return
+  // null.
+  void reset(const T* p_value) {
+    ptr_.reset(p_value);
+  }
+
+  // Make the NotifyValueChanged() public for FakeVariables.
+  void NotifyValueChanged() {
+    Variable<T>::NotifyValueChanged();
+  }
+
+ protected:
+  // Variable<T> overrides.
+  // Returns the pointer set with reset(). The ownership of the object is passed
+  // to the caller and the pointer is release from the FakeVariable. A second
+  // call to GetValue() without reset() will return null and set the error
+  // message.
+  const T* GetValue(base::TimeDelta /* timeout */,
+                    std::string* errmsg) override {
+    if (ptr_ == nullptr && errmsg != nullptr)
+      *errmsg = this->GetName() + " is an empty FakeVariable";
+    // Passes the pointer ownership to the caller.
+    return ptr_.release();
+  }
+
+ private:
+  // The pointer returned by GetValue().
+  std::unique_ptr<const T> ptr_;
+
+  DISALLOW_COPY_AND_ASSIGN(FakeVariable);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_FAKE_VARIABLE_H_
diff --git a/update_manager/generic_variables.h b/update_manager/generic_variables.h
new file mode 100644
index 0000000..f87a05e
--- /dev/null
+++ b/update_manager/generic_variables.h
@@ -0,0 +1,218 @@
+//
+// Copyright (C) 2014 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.
+//
+
+// Generic and provider-independent Variable subclasses. These variables can be
+// used by any state provider to implement simple variables to avoid repeat the
+// same common code on different state providers.
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_GENERIC_VARIABLES_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_GENERIC_VARIABLES_H_
+
+#include <string>
+
+#include <base/callback.h>
+
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Variable class returning a copy of a given object using the copy constructor.
+// This template class can be used to define variables that expose as a variable
+// any fixed object, such as the a provider's private member. The variable will
+// create copies of the provided object using the copy constructor of that
+// class.
+//
+// For example, a state provider exposing a private member as a variable can
+// implement this as follows:
+//
+//   class SomethingProvider {
+//    public:
+//      SomethingProvider(...) {
+//        var_something_foo = new PollCopyVariable<MyType>(foo_);
+//      }
+//      ...
+//    private:
+//     MyType foo_;
+//   };
+template<typename T>
+class PollCopyVariable : public Variable<T> {
+ public:
+  // Creates the variable returning copies of the passed |ref|. The reference to
+  // this object is kept and it should be available whenever the GetValue()
+  // method is called. If |is_set_p| is not null, then this flag will be
+  // consulted prior to returning the value, and an |errmsg| will be returned if
+  // it is not set.
+  PollCopyVariable(const std::string& name, const T& ref, const bool* is_set_p,
+                   const std::string& errmsg)
+      : Variable<T>(name, kVariableModePoll), ref_(ref), is_set_p_(is_set_p),
+        errmsg_(errmsg) {}
+  PollCopyVariable(const std::string& name, const T& ref, const bool* is_set_p)
+      : PollCopyVariable(name, ref, is_set_p, std::string()) {}
+  PollCopyVariable(const std::string& name, const T& ref)
+      : PollCopyVariable(name, ref, nullptr) {}
+
+  PollCopyVariable(const std::string& name, const base::TimeDelta poll_interval,
+                   const T& ref, const bool* is_set_p,
+                   const std::string& errmsg)
+      : Variable<T>(name, poll_interval), ref_(ref), is_set_p_(is_set_p),
+        errmsg_(errmsg) {}
+  PollCopyVariable(const std::string& name, const base::TimeDelta poll_interval,
+                   const T& ref, const bool* is_set_p)
+      : PollCopyVariable(name, poll_interval, ref, is_set_p, std::string()) {}
+  PollCopyVariable(const std::string& name, const base::TimeDelta poll_interval,
+                   const T& ref)
+      : PollCopyVariable(name, poll_interval, ref, nullptr) {}
+
+ protected:
+  FRIEND_TEST(UmPollCopyVariableTest, SimpleTest);
+  FRIEND_TEST(UmPollCopyVariableTest, UseCopyConstructorTest);
+
+  // Variable override.
+  inline const T* GetValue(base::TimeDelta /* timeout */,
+                           std::string* errmsg) override {
+    if (is_set_p_ && !(*is_set_p_)) {
+      if (errmsg) {
+        if (errmsg_.empty())
+          *errmsg = "No value set for " + this->GetName();
+        else
+          *errmsg = errmsg_;
+      }
+      return nullptr;
+    }
+    return new T(ref_);
+  }
+
+ private:
+  // Reference to the object to be copied by GetValue().
+  const T& ref_;
+
+  // A pointer to a flag indicating whether the value is set. If null, then the
+  // value is assumed to be set.
+  const bool* const is_set_p_;
+
+  // An error message to be returned when attempting to get an unset value.
+  const std::string errmsg_;
+};
+
+// Variable class returning a constant value that is cached on the variable when
+// it is created.
+template<typename T>
+class ConstCopyVariable : public Variable<T> {
+ public:
+  // Creates the variable returning copies of the passed |obj|. The value passed
+  // is copied in this variable, and new copies of it will be returned by
+  // GetValue().
+  ConstCopyVariable(const std::string& name, const T& obj)
+      : Variable<T>(name, kVariableModeConst), obj_(obj) {}
+
+ protected:
+  // Variable override.
+  const T* GetValue(base::TimeDelta /* timeout */,
+                    std::string* /* errmsg */) override {
+    return new T(obj_);
+  }
+
+ private:
+  // Value to be copied by GetValue().
+  const T obj_;
+};
+
+// Variable class returning a copy of a value returned by a given function. The
+// function is called every time the variable is being polled.
+template<typename T>
+class CallCopyVariable : public Variable<T> {
+ public:
+  CallCopyVariable(const std::string& name, base::Callback<T(void)> func)
+      : Variable<T>(name, kVariableModePoll), func_(func) {}
+  CallCopyVariable(const std::string& name,
+                   const base::TimeDelta poll_interval,
+                   base::Callback<T(void)> func)
+      : Variable<T>(name, poll_interval), func_(func) {}
+
+ protected:
+  // Variable override.
+  const T* GetValue(base::TimeDelta /* timeout */,
+                    std::string* /* errmsg */) override {
+    if (func_.is_null())
+      return nullptr;
+    return new T(func_.Run());
+  }
+
+ private:
+  FRIEND_TEST(UmCallCopyVariableTest, SimpleTest);
+
+  // The function to be called, stored as a base::Callback.
+  base::Callback<T(void)> func_;
+
+  DISALLOW_COPY_AND_ASSIGN(CallCopyVariable);
+};
+
+
+// A Variable class to implement simple Async variables. It provides two methods
+// SetValue and UnsetValue to modify the current value of the variable and
+// notify the registered observers whenever the value changed.
+//
+// The type T needs to be copy-constructible, default-constructible and have an
+// operator== (to determine if the value changed), which makes this class
+// suitable for basic types.
+template<typename T>
+class AsyncCopyVariable : public Variable<T> {
+ public:
+  explicit AsyncCopyVariable(const std::string& name)
+      : Variable<T>(name, kVariableModeAsync), has_value_(false) {}
+
+  AsyncCopyVariable(const std::string& name, const T value)
+      : Variable<T>(name, kVariableModeAsync),
+        has_value_(true), value_(value) {}
+
+  void SetValue(const T& new_value) {
+    bool should_notify = !(has_value_ && new_value == value_);
+    value_ = new_value;
+    has_value_ = true;
+    if (should_notify)
+      this->NotifyValueChanged();
+  }
+
+  void UnsetValue() {
+    if (has_value_) {
+      has_value_ = false;
+      this->NotifyValueChanged();
+    }
+  }
+
+ protected:
+  // Variable override.
+  const T* GetValue(base::TimeDelta /* timeout */,
+                    std::string* errmsg) override {
+    if (!has_value_) {
+      if (errmsg)
+        *errmsg = "No value set for " + this->GetName();
+      return nullptr;
+    }
+    return new T(value_);
+  }
+
+ private:
+  // Whether the variable has a value set.
+  bool has_value_;
+
+  // Copy of the object to be returned by GetValue().
+  T value_;
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_GENERIC_VARIABLES_H_
diff --git a/update_manager/generic_variables_unittest.cc b/update_manager/generic_variables_unittest.cc
new file mode 100644
index 0000000..cb0c48f
--- /dev/null
+++ b/update_manager/generic_variables_unittest.cc
@@ -0,0 +1,224 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/generic_variables.h"
+
+#include <memory>
+
+#include <base/callback.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/update_manager/umtest_utils.h"
+
+using brillo::MessageLoop;
+using brillo::MessageLoopRunMaxIterations;
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+class UmPollCopyVariableTest : public ::testing::Test {};
+
+
+TEST_F(UmPollCopyVariableTest, SimpleTest) {
+  // Tests that copies are generated as intended.
+  int source = 5;
+  PollCopyVariable<int> var("var", source);
+
+  // Generate and validate a copy.
+  unique_ptr<const int> copy_1(var.GetValue(
+          UmTestUtils::DefaultTimeout(), nullptr));
+  ASSERT_NE(nullptr, copy_1.get());
+  EXPECT_EQ(5, *copy_1);
+
+  // Assign a different value to the source variable.
+  source = 42;
+
+  // Check that the content of the copy was not affected (distinct instance).
+  EXPECT_EQ(5, *copy_1);
+
+  // Generate and validate a second copy.
+  UmTestUtils::ExpectVariableHasValue(42, &var);
+}
+
+TEST_F(UmPollCopyVariableTest, SetFlagTest) {
+  // Tests that the set flag is being referred to as expected.
+  int source = 5;
+  bool is_set = false;
+  PollCopyVariable<int> var("var", source, &is_set);
+
+  // Flag marked unset, nothing should be returned.
+  UmTestUtils::ExpectVariableNotSet(&var);
+
+  // Flag marked set, we should be getting a value.
+  is_set = true;
+  UmTestUtils::ExpectVariableHasValue(5, &var);
+}
+
+
+class CopyConstructorTestClass {
+ public:
+  CopyConstructorTestClass(void) : copied_(false) {}
+  CopyConstructorTestClass(const CopyConstructorTestClass& other)
+      : copied_(true), val_(other.val_ * 2) {}
+
+  // Tells if the instance was constructed using the copy-constructor.
+  const bool copied_;
+
+  // An auxiliary internal value.
+  int val_ = 0;
+};
+
+
+TEST_F(UmPollCopyVariableTest, UseCopyConstructorTest) {
+  // Ensures that CopyVariables indeed uses the copy constructor.
+  const CopyConstructorTestClass source;
+  ASSERT_FALSE(source.copied_);
+
+  PollCopyVariable<CopyConstructorTestClass> var("var", source);
+  unique_ptr<const CopyConstructorTestClass> copy(
+      var.GetValue(UmTestUtils::DefaultTimeout(), nullptr));
+  ASSERT_NE(nullptr, copy.get());
+  EXPECT_TRUE(copy->copied_);
+}
+
+
+class UmConstCopyVariableTest : public ::testing::Test {};
+
+TEST_F(UmConstCopyVariableTest, SimpleTest) {
+  int source = 5;
+  ConstCopyVariable<int> var("var", source);
+  UmTestUtils::ExpectVariableHasValue(5, &var);
+
+  // Ensure the value is cached.
+  source = 42;
+  UmTestUtils::ExpectVariableHasValue(5, &var);
+}
+
+
+class UmCallCopyVariableTest : public ::testing::Test {};
+
+CopyConstructorTestClass test_func(CopyConstructorTestClass* obj) {
+  obj->val_++;  // So we can check that the function was called.
+  return *obj;
+}
+
+TEST_F(UmCallCopyVariableTest, SimpleTest) {
+  // Tests that the returned value is generated by copying the value returned by
+  // the function call.
+
+  CopyConstructorTestClass test_obj;
+  ASSERT_FALSE(test_obj.copied_);
+  test_obj.val_ = 5;
+
+  base::Callback<CopyConstructorTestClass(void)> cb = base::Bind(
+      test_func, &test_obj);
+  CallCopyVariable<CopyConstructorTestClass> var("var", cb);
+
+  unique_ptr<const CopyConstructorTestClass> copy(
+      var.GetValue(UmTestUtils::DefaultTimeout(), nullptr));
+  EXPECT_EQ(6, test_obj.val_);  // Check that the function was called.
+  ASSERT_NE(nullptr, copy.get());
+  EXPECT_TRUE(copy->copied_);
+  EXPECT_EQ(12, copy->val_);  // Check that copying occurred once.
+}
+
+TEST_F(UmCallCopyVariableTest, NullTest) {
+  // Ensures that the variable returns null when the callback is null.
+
+  base::Callback<bool(void)> cb;
+  CallCopyVariable<bool> var("var", cb);
+  UmTestUtils::ExpectVariableNotSet(&var);
+}
+
+class UmAsyncCopyVariableTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+  }
+
+  void TearDown() override {
+    // No remaining event on the main loop.
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+
+  brillo::FakeMessageLoop loop_{nullptr};
+};
+
+TEST_F(UmAsyncCopyVariableTest, ConstructorTest) {
+  AsyncCopyVariable<int> var("var");
+  UmTestUtils::ExpectVariableNotSet(&var);
+  EXPECT_EQ(kVariableModeAsync, var.GetMode());
+}
+
+TEST_F(UmAsyncCopyVariableTest, SetValueTest) {
+  AsyncCopyVariable<int> var("var");
+  var.SetValue(5);
+  UmTestUtils::ExpectVariableHasValue(5, &var);
+  // Execute all the pending observers.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+}
+
+TEST_F(UmAsyncCopyVariableTest, UnsetValueTest) {
+  AsyncCopyVariable<int> var("var", 42);
+  var.UnsetValue();
+  UmTestUtils::ExpectVariableNotSet(&var);
+  // Execute all the pending observers.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+}
+
+class CallCounterObserver : public BaseVariable::ObserverInterface {
+ public:
+  void ValueChanged(BaseVariable* variable) {
+    calls_count_++;
+  }
+
+  int calls_count_ = 0;
+};
+
+TEST_F(UmAsyncCopyVariableTest, ObserverCalledTest) {
+  AsyncCopyVariable<int> var("var", 42);
+  CallCounterObserver observer;
+  var.AddObserver(&observer);
+  EXPECT_EQ(0, observer.calls_count_);
+
+  // Check that a different value fires the notification.
+  var.SetValue(5);
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(1, observer.calls_count_);
+
+  // Check the same value doesn't.
+  var.SetValue(5);
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(1, observer.calls_count_);
+
+  // Check that unsetting a previously set value fires the notification.
+  var.UnsetValue();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(2, observer.calls_count_);
+
+  // Check that unsetting again doesn't.
+  var.UnsetValue();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(2, observer.calls_count_);
+
+  var.RemoveObserver(&observer);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/mock_policy.h b/update_manager/mock_policy.h
new file mode 100644
index 0000000..14470e9
--- /dev/null
+++ b/update_manager/mock_policy.h
@@ -0,0 +1,92 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_MOCK_POLICY_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_MOCK_POLICY_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/update_manager/default_policy.h"
+#include "update_engine/update_manager/policy.h"
+
+namespace chromeos_update_manager {
+
+// A mocked implementation of Policy.
+class MockPolicy : public Policy {
+ public:
+  explicit MockPolicy(chromeos_update_engine::ClockInterface* clock)
+      : default_policy_(clock) {
+    // We defer to the corresponding DefaultPolicy methods, by default.
+    ON_CALL(*this, UpdateCheckAllowed(testing::_, testing::_, testing::_,
+                                      testing::_))
+        .WillByDefault(testing::Invoke(
+                &default_policy_, &DefaultPolicy::UpdateCheckAllowed));
+    ON_CALL(*this, UpdateCanStart(testing::_, testing::_, testing::_,
+                                  testing::_, testing::_))
+        .WillByDefault(testing::Invoke(
+                &default_policy_, &DefaultPolicy::UpdateCanStart));
+    ON_CALL(*this, UpdateDownloadAllowed(testing::_, testing::_, testing::_,
+                                         testing::_))
+        .WillByDefault(testing::Invoke(
+                &default_policy_, &DefaultPolicy::UpdateDownloadAllowed));
+    ON_CALL(*this, P2PEnabled(testing::_, testing::_, testing::_, testing::_))
+        .WillByDefault(testing::Invoke(
+                &default_policy_, &DefaultPolicy::P2PEnabled));
+    ON_CALL(*this, P2PEnabledChanged(testing::_, testing::_, testing::_,
+                                     testing::_, testing::_))
+        .WillByDefault(testing::Invoke(
+                &default_policy_, &DefaultPolicy::P2PEnabledChanged));
+  }
+
+  MockPolicy() : MockPolicy(nullptr) {}
+  ~MockPolicy() override {}
+
+  // Policy overrides.
+  MOCK_CONST_METHOD4(UpdateCheckAllowed,
+                     EvalStatus(EvaluationContext*, State*, std::string*,
+                                UpdateCheckParams*));
+
+  MOCK_CONST_METHOD5(UpdateCanStart,
+                     EvalStatus(EvaluationContext*, State*, std::string*,
+                                UpdateDownloadParams*, UpdateState));
+
+  MOCK_CONST_METHOD4(UpdateDownloadAllowed,
+                     EvalStatus(EvaluationContext*, State*, std::string*,
+                                bool*));
+
+  MOCK_CONST_METHOD4(P2PEnabled,
+                     EvalStatus(EvaluationContext*, State*, std::string*,
+                                bool*));
+
+  MOCK_CONST_METHOD5(P2PEnabledChanged,
+                     EvalStatus(EvaluationContext*, State*, std::string*,
+                                bool*, bool));
+
+ protected:
+  // Policy override.
+  std::string PolicyName() const override { return "MockPolicy"; }
+
+ private:
+  DefaultPolicy default_policy_;
+
+  DISALLOW_COPY_AND_ASSIGN(MockPolicy);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_MOCK_POLICY_H_
diff --git a/update_manager/mock_variable.h b/update_manager/mock_variable.h
new file mode 100644
index 0000000..1493491
--- /dev/null
+++ b/update_manager/mock_variable.h
@@ -0,0 +1,42 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_MOCK_VARIABLE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_MOCK_VARIABLE_H_
+
+#include <string>
+
+#include <gmock/gmock.h>
+
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// This is a generic mock of the Variable class.
+template<typename T>
+class MockVariable : public Variable<T> {
+ public:
+  using Variable<T>::Variable;
+
+  MOCK_METHOD2_T(GetValue, const T*(base::TimeDelta, std::string*));
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(MockVariable);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_MOCK_VARIABLE_H_
diff --git a/update_manager/policy.cc b/update_manager/policy.cc
new file mode 100644
index 0000000..151c225
--- /dev/null
+++ b/update_manager/policy.cc
@@ -0,0 +1,37 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/policy.h"
+
+#include <string>
+
+using std::string;
+
+namespace chromeos_update_manager {
+
+string ToString(EvalStatus status) {
+  switch (status) {
+    case EvalStatus::kFailed:
+      return "kFailed";
+    case EvalStatus::kSucceeded:
+      return "kSucceeded";
+    case EvalStatus::kAskMeAgainLater:
+      return "kAskMeAgainLater";
+  }
+  return "Invalid";
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/policy.h b/update_manager/policy.h
new file mode 100644
index 0000000..fae1494
--- /dev/null
+++ b/update_manager/policy.h
@@ -0,0 +1,290 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_POLICY_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_POLICY_H_
+
+#include <string>
+#include <tuple>
+#include <vector>
+
+#include "update_engine/common/error_code.h"
+#include "update_engine/update_manager/evaluation_context.h"
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+// The three different results of a policy request.
+enum class EvalStatus {
+  kFailed,
+  kSucceeded,
+  kAskMeAgainLater,
+};
+
+std::string ToString(EvalStatus status);
+
+// Parameters of an update check. These parameters are determined by the
+// UpdateCheckAllowed policy.
+struct UpdateCheckParams {
+  bool updates_enabled;  // Whether the auto-updates are enabled on this build.
+
+  // Attributes pertaining to the case where update checks are allowed.
+  //
+  // A target version prefix, if imposed by policy; otherwise, an empty string.
+  std::string target_version_prefix;
+  // A target channel, if so imposed by policy; otherwise, an empty string.
+  std::string target_channel;
+
+  // Whether the allowed update is interactive (user-initiated) or periodic.
+  bool is_interactive;
+};
+
+// Input arguments to UpdateCanStart.
+//
+// A snapshot of the state of the current update process. This includes
+// everything that a policy might need and that occurred since the first time
+// the current payload was first seen and attempted (consecutively).
+struct UpdateState {
+  // Information pertaining to the current update payload and/or check.
+  //
+  // Whether the current update check is an interactive one. The caller should
+  // feed the value returned by the preceding call to UpdateCheckAllowed().
+  bool is_interactive;
+  // Whether it is a delta payload.
+  bool is_delta_payload;
+  // Wallclock time when payload was first (consecutively) offered by Omaha.
+  base::Time first_seen;
+  // Number of consecutive update checks returning the current update.
+  int num_checks;
+  // Number of update payload failures and the wallclock time when it was last
+  // updated by the updater. These should both be nullified whenever a new
+  // update is seen; they are updated at the policy's descretion (via
+  // UpdateDownloadParams.do_increment_failures) once all of the usable download
+  // URLs for the payload have been used without success. They should be
+  // persisted across reboots.
+  int num_failures;
+  base::Time failures_last_updated;
+
+  // Information pertaining to downloading and applying of the current update.
+  //
+  // An array of download URLs provided by Omaha.
+  std::vector<std::string> download_urls;
+  // Max number of errors allowed per download URL.
+  int download_errors_max;
+  // The index of the URL to download from, as determined in the previous call
+  // to the policy. For a newly seen payload, this should be -1.
+  int last_download_url_idx;
+  // The number of successive download errors pertaining to this last URL, as
+  // determined in the previous call to the policy. For a newly seen payload,
+  // this should be zero.
+  int last_download_url_num_errors;
+  // An array of errors that occurred while trying to download this update since
+  // the previous call to this policy has returned, or since this payload was
+  // first seen, or since the updater process has started (whichever is later).
+  // Includes the URL index attempted, the error code, and the wallclock-based
+  // timestamp when it occurred.
+  std::vector<std::tuple<int, chromeos_update_engine::ErrorCode, base::Time>>
+      download_errors;
+  // Whether Omaha forbids use of P2P for downloading and/or sharing.
+  bool p2p_downloading_disabled;
+  bool p2p_sharing_disabled;
+  // The number of P2P download attempts and wallclock-based time when P2P
+  // download was first attempted.
+  int p2p_num_attempts;
+  base::Time p2p_first_attempted;
+
+  // Information pertaining to update backoff mechanism.
+  //
+  // The currently known (persisted) wallclock-based backoff expiration time;
+  // zero if none.
+  base::Time backoff_expiry;
+  // Whether backoff is disabled by Omaha.
+  bool is_backoff_disabled;
+
+  // Information pertaining to update scattering.
+  //
+  // The currently knwon (persisted) scattering wallclock-based wait period and
+  // update check threshold; zero if none.
+  base::TimeDelta scatter_wait_period;
+  int scatter_check_threshold;
+  // Maximum wait period allowed for this update, as determined by Omaha.
+  base::TimeDelta scatter_wait_period_max;
+  // Minimum/maximum check threshold values.
+  // TODO(garnold) These appear to not be related to the current update and so
+  // should probably be obtained as variables via UpdaterProvider.
+  int scatter_check_threshold_min;
+  int scatter_check_threshold_max;
+};
+
+// Results regarding the downloading and applying of an update, as determined by
+// UpdateCanStart.
+//
+// An enumerator for the reasons of not allowing an update to start.
+enum class UpdateCannotStartReason {
+  kUndefined,
+  kCheckDue,
+  kScattering,
+  kBackoff,
+  kCannotDownload,
+};
+
+struct UpdateDownloadParams {
+  // Whether the update attempt is allowed to proceed.
+  bool update_can_start;
+  // If update cannot proceed, a reason code for why it cannot do so.
+  UpdateCannotStartReason cannot_start_reason;
+
+  // Download related attributes. The update engine uses them to choose the
+  // means for downloading and applying an update.
+  //
+  // The index of the download URL to use (-1 means no suitable URL was found)
+  // and whether it can be used. Even if there's no URL or its use is not
+  // allowed (backoff, scattering) there may still be other means for download
+  // (like P2P).  The URL index needs to be persisted and handed back to the
+  // policy on the next time it is called.
+  int download_url_idx;
+  bool download_url_allowed;
+  // The number of download errors associated with this download URL. This value
+  // needs to be persisted and handed back to the policy on the next time it is
+  // called.
+  int download_url_num_errors;
+  // Whether P2P download and sharing are allowed.
+  bool p2p_downloading_allowed;
+  bool p2p_sharing_allowed;
+
+  // Other values that need to be persisted and handed to the policy as need on
+  // the next call.
+  //
+  // Whether an update failure has been identified by the policy. The client
+  // should increment and persist its update failure count, and record the time
+  // when this was done; it needs to hand these values back to the policy
+  // (UpdateState.{num_failures,failures_last_updated}) on the next time it is
+  // called.
+  bool do_increment_failures;
+  // The current backof expiry.
+  base::Time backoff_expiry;
+  // The scattering wait period and check threshold.
+  base::TimeDelta scatter_wait_period;
+  int scatter_check_threshold;
+};
+
+// The Policy class is an interface to the ensemble of policy requests that the
+// client can make. A derived class includes the policy implementations of
+// these.
+//
+// When compile-time selection of the policy is required due to missing or extra
+// parts in a given platform, a different Policy subclass can be used.
+class Policy {
+ public:
+  virtual ~Policy() {}
+
+  // Returns the name of a public policy request.
+  // IMPORTANT: Be sure to add a conditional for each new public policy that is
+  // being added to this class in the future.
+  template<typename R, typename... Args>
+  std::string PolicyRequestName(
+      EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                          std::string*, R*,
+                                          Args...) const) const {
+    std::string class_name = PolicyName() + "::";
+
+    if (reinterpret_cast<typeof(&Policy::UpdateCheckAllowed)>(
+            policy_method) == &Policy::UpdateCheckAllowed)
+      return class_name + "UpdateCheckAllowed";
+    if (reinterpret_cast<typeof(&Policy::UpdateCanStart)>(
+            policy_method) == &Policy::UpdateCanStart)
+      return class_name + "UpdateCanStart";
+    if (reinterpret_cast<typeof(&Policy::UpdateDownloadAllowed)>(
+            policy_method) == &Policy::UpdateDownloadAllowed)
+      return class_name + "UpdateDownloadAllowed";
+    if (reinterpret_cast<typeof(&Policy::P2PEnabled)>(
+            policy_method) == &Policy::P2PEnabled)
+      return class_name + "P2PEnabled";
+    if (reinterpret_cast<typeof(&Policy::P2PEnabledChanged)>(
+            policy_method) == &Policy::P2PEnabledChanged)
+      return class_name + "P2PEnabledChanged";
+
+    NOTREACHED();
+    return class_name + "(unknown)";
+  }
+
+
+  // List of policy requests. A policy request takes an EvaluationContext as the
+  // first argument, a State instance, a returned error message, a returned
+  // value and optionally followed by one or more arbitrary constant arguments.
+  //
+  // When the implementation fails, the method returns EvalStatus::kFailed and
+  // sets the |error| string.
+
+  // UpdateCheckAllowed returns whether it is allowed to request an update check
+  // to Omaha.
+  virtual EvalStatus UpdateCheckAllowed(
+      EvaluationContext* ec, State* state, std::string* error,
+      UpdateCheckParams* result) const = 0;
+
+  // Returns EvalStatus::kSucceeded if either an update can start being
+  // processed, or the attempt needs to be aborted. In cases where the update
+  // needs to wait for some condition to be satisfied, but none of the values
+  // that need to be persisted has changed, returns
+  // EvalStatus::kAskMeAgainLater. Arguments include an |update_state| that
+  // encapsulates data pertaining to the current ongoing update process.
+  virtual EvalStatus UpdateCanStart(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      UpdateDownloadParams* result,
+      UpdateState update_state) const = 0;
+
+  // Checks whether downloading of an update is allowed; currently, this checks
+  // whether the network connection type is suitable for updating over.  May
+  // consult the shill provider as well as the device policy (if available).
+  // Returns |EvalStatus::kSucceeded|, setting |result| according to whether or
+  // not the current connection can be used; on error, returns
+  // |EvalStatus::kFailed| and sets |error| accordingly.
+  virtual EvalStatus UpdateDownloadAllowed(
+      EvaluationContext* ec,
+      State* state,
+      std::string* error,
+      bool* result) const = 0;
+
+  // Checks whether P2P is enabled. This may consult device policy and other
+  // global settings.
+  virtual EvalStatus P2PEnabled(
+      EvaluationContext* ec, State* state, std::string* error,
+      bool* result) const = 0;
+
+  // Checks whether P2P is enabled, but blocks (returns
+  // |EvalStatus::kAskMeAgainLater|) until it is different from |prev_result|.
+  // If the P2P enabled status is not expected to change, will return
+  // immediately with |EvalStatus::kSucceeded|. This internally uses the
+  // P2PEnabled() policy above.
+  virtual EvalStatus P2PEnabledChanged(
+      EvaluationContext* ec, State* state, std::string* error,
+      bool* result, bool prev_result) const = 0;
+
+ protected:
+  Policy() {}
+
+  // Returns the name of the actual policy class.
+  virtual std::string PolicyName() const = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(Policy);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_POLICY_H_
diff --git a/update_manager/policy_utils.h b/update_manager/policy_utils.h
new file mode 100644
index 0000000..960987e
--- /dev/null
+++ b/update_manager/policy_utils.h
@@ -0,0 +1,38 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_POLICY_UTILS_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_POLICY_UTILS_H_
+
+#include "update_engine/update_manager/policy.h"
+
+// Checks that the passed pointer value is not null, returning kFailed on the
+// current context and setting the *error description when it is null. The
+// intended use is to validate variable failures while using
+// EvaluationContext::GetValue, for example:
+//
+//   const int* my_value = ec->GetValue(state->my_provider()->var_my_value());
+//   POLICY_CHECK_VALUE_AND_FAIL(my_value, error);
+//
+#define POLICY_CHECK_VALUE_AND_FAIL(ptr, error) \
+    do { \
+      if ((ptr) == nullptr) { \
+        *(error) = #ptr " is required but is null."; \
+        return EvalStatus::kFailed; \
+      } \
+    } while (false)
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_POLICY_UTILS_H_
diff --git a/update_manager/prng.h b/update_manager/prng.h
new file mode 100644
index 0000000..64f886c
--- /dev/null
+++ b/update_manager/prng.h
@@ -0,0 +1,51 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_PRNG_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_PRNG_H_
+
+#include <random>
+
+#include <base/logging.h>
+
+namespace chromeos_update_manager {
+
+// A thread-safe, unsecure, 32-bit pseudo-random number generator based on
+// std::mt19937.
+class PRNG {
+ public:
+  // Initializes the generator with the passed |seed| value.
+  explicit PRNG(uint32_t seed) : gen_(seed) {}
+
+  // Returns a random unsigned 32-bit integer.
+  uint32_t Rand() { return gen_(); }
+
+  // Returns a random integer uniformly distributed in the range [min, max].
+  int RandMinMax(int min, int max) {
+    DCHECK_LE(min, max);
+    return std::uniform_int_distribution<>(min, max)(gen_);
+  }
+
+ private:
+  // A pseudo-random number generator.
+  std::mt19937 gen_;
+
+  DISALLOW_COPY_AND_ASSIGN(PRNG);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_PRNG_H_
diff --git a/update_manager/prng_unittest.cc b/update_manager/prng_unittest.cc
new file mode 100644
index 0000000..2a3f689
--- /dev/null
+++ b/update_manager/prng_unittest.cc
@@ -0,0 +1,79 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/prng.h"
+
+#include <vector>
+
+#include <gtest/gtest.h>
+
+using std::vector;
+
+namespace chromeos_update_manager {
+
+TEST(UmPRNGTest, ShouldBeDeterministic) {
+  PRNG a(42);
+  PRNG b(42);
+
+  for (int i = 0; i < 1000; ++i) {
+    EXPECT_EQ(a.Rand(), b.Rand()) << "Iteration i=" << i;
+  }
+}
+
+TEST(UmPRNGTest, SeedChangesGeneratedSequence) {
+  PRNG a(42);
+  PRNG b(5);
+
+  vector<uint32_t> values_a;
+  vector<uint32_t> values_b;
+
+  for (int i = 0; i < 100; ++i) {
+    values_a.push_back(a.Rand());
+    values_b.push_back(b.Rand());
+  }
+  EXPECT_NE(values_a, values_b);
+}
+
+TEST(UmPRNGTest, IsNotConstant) {
+  PRNG prng(5);
+
+  uint32_t initial_value = prng.Rand();
+  bool prng_is_constant = true;
+  for (int i = 0; i < 100; ++i) {
+    if (prng.Rand() != initial_value) {
+      prng_is_constant = false;
+      break;
+    }
+  }
+  EXPECT_FALSE(prng_is_constant) << "After 100 iterations.";
+}
+
+TEST(UmPRNGTest, RandCoversRange) {
+  PRNG a(42);
+  int hits[11] = { 0 };
+
+  for (int i = 0; i < 1000; i++) {
+    int r = a.RandMinMax(0, 10);
+    ASSERT_LE(0, r);
+    ASSERT_GE(10, r);
+    hits[r]++;
+  }
+
+  for (auto& hit : hits)
+    EXPECT_LT(0, hit);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/provider.h b/update_manager/provider.h
new file mode 100644
index 0000000..84335a2
--- /dev/null
+++ b/update_manager/provider.h
@@ -0,0 +1,38 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_PROVIDER_H_
+
+#include <base/macros.h>
+
+namespace chromeos_update_manager {
+
+// Abstract base class for a policy provider.
+class Provider {
+ public:
+  virtual ~Provider() {}
+
+ protected:
+  Provider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(Provider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_PROVIDER_H_
diff --git a/update_manager/random_provider.h b/update_manager/random_provider.h
new file mode 100644
index 0000000..60df62d
--- /dev/null
+++ b/update_manager/random_provider.h
@@ -0,0 +1,45 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_RANDOM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_RANDOM_PROVIDER_H_
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Provider of random values.
+class RandomProvider : public Provider {
+ public:
+  ~RandomProvider() override {}
+
+  // Return a random number every time it is requested. Note that values
+  // returned by the variables are cached by the EvaluationContext, so the
+  // returned value will be the same during the same policy request. If more
+  // random values are needed use a PRNG seeded with this value.
+  virtual Variable<uint64_t>* var_seed() = 0;
+
+ protected:
+  RandomProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(RandomProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_RANDOM_PROVIDER_H_
diff --git a/update_manager/real_config_provider.cc b/update_manager/real_config_provider.cc
new file mode 100644
index 0000000..2d17a7f
--- /dev/null
+++ b/update_manager/real_config_provider.cc
@@ -0,0 +1,64 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_config_provider.h"
+
+#include <base/files/file_path.h>
+#include <base/logging.h>
+#include <brillo/key_value_store.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/generic_variables.h"
+
+using brillo::KeyValueStore;
+
+namespace {
+
+const char* kConfigFilePath = "/etc/update_manager.conf";
+
+// Config options:
+const char* kConfigOptsIsOOBEEnabled = "is_oobe_enabled";
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+bool RealConfigProvider::Init() {
+  KeyValueStore store;
+
+  if (hardware_->IsNormalBootMode()) {
+    store.Load(base::FilePath(root_prefix_ + kConfigFilePath));
+  } else {
+    if (store.Load(base::FilePath(root_prefix_ +
+                                  chromeos_update_engine::kStatefulPartition +
+                                  kConfigFilePath))) {
+      LOG(INFO) << "UpdateManager Config loaded from stateful partition.";
+    } else {
+      store.Load(base::FilePath(root_prefix_ + kConfigFilePath));
+    }
+  }
+
+  bool is_oobe_enabled;
+  if (!store.GetBoolean(kConfigOptsIsOOBEEnabled, &is_oobe_enabled))
+    is_oobe_enabled = true;  // Default value.
+  var_is_oobe_enabled_.reset(
+      new ConstCopyVariable<bool>(kConfigOptsIsOOBEEnabled, is_oobe_enabled));
+
+  return true;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_config_provider.h b/update_manager/real_config_provider.h
new file mode 100644
index 0000000..4de910c
--- /dev/null
+++ b/update_manager/real_config_provider.h
@@ -0,0 +1,65 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_CONFIG_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_CONFIG_PROVIDER_H_
+
+#include <memory>
+#include <string>
+
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/update_manager/config_provider.h"
+#include "update_engine/update_manager/generic_variables.h"
+
+namespace chromeos_update_manager {
+
+// ConfigProvider concrete implementation.
+class RealConfigProvider : public ConfigProvider {
+ public:
+  explicit RealConfigProvider(
+      chromeos_update_engine::HardwareInterface* hardware)
+      : hardware_(hardware) {}
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+  Variable<bool>* var_is_oobe_enabled() override {
+    return var_is_oobe_enabled_.get();
+  }
+
+ private:
+  friend class UmRealConfigProviderTest;
+
+  // Used for testing. Sets the root prefix, which is by default "". Call this
+  // method before calling Init() in order to mock out the place where the files
+  // are being read from.
+  void SetRootPrefix(const std::string& prefix) {
+    root_prefix_ = prefix;
+  }
+
+  std::unique_ptr<ConstCopyVariable<bool>> var_is_oobe_enabled_;
+
+  chromeos_update_engine::HardwareInterface* hardware_;
+
+  // Prefix to prepend to the file paths. Useful for testing.
+  std::string root_prefix_;
+
+  DISALLOW_COPY_AND_ASSIGN(RealConfigProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_CONFIG_PROVIDER_H_
diff --git a/update_manager/real_config_provider_unittest.cc b/update_manager/real_config_provider_unittest.cc
new file mode 100644
index 0000000..2d7dc0d
--- /dev/null
+++ b/update_manager/real_config_provider_unittest.cc
@@ -0,0 +1,102 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_config_provider.h"
+
+#include <memory>
+
+#include <base/files/file_util.h>
+#include <base/files/scoped_temp_dir.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/constants.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::TimeDelta;
+using chromeos_update_engine::test_utils::WriteFileString;
+using std::string;
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+class UmRealConfigProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    ASSERT_TRUE(root_dir_.CreateUniqueTempDir());
+    provider_.reset(new RealConfigProvider(&fake_hardware_));
+    provider_->SetRootPrefix(root_dir_.path().value());
+  }
+
+  void WriteStatefulConfig(const string& config) {
+    base::FilePath kFile(root_dir_.path().value()
+                         + chromeos_update_engine::kStatefulPartition
+                         + "/etc/update_manager.conf");
+    ASSERT_TRUE(base::CreateDirectory(kFile.DirName()));
+    ASSERT_TRUE(WriteFileString(kFile.value(), config));
+  }
+
+  void WriteRootfsConfig(const string& config) {
+    base::FilePath kFile(root_dir_.path().value()
+                         + "/etc/update_manager.conf");
+    ASSERT_TRUE(base::CreateDirectory(kFile.DirName()));
+    ASSERT_TRUE(WriteFileString(kFile.value(), config));
+  }
+
+  unique_ptr<RealConfigProvider> provider_;
+  chromeos_update_engine::FakeHardware fake_hardware_;
+  TimeDelta default_timeout_ = TimeDelta::FromSeconds(1);
+  base::ScopedTempDir root_dir_;
+};
+
+TEST_F(UmRealConfigProviderTest, InitTest) {
+  EXPECT_TRUE(provider_->Init());
+  EXPECT_NE(nullptr, provider_->var_is_oobe_enabled());
+}
+
+TEST_F(UmRealConfigProviderTest, NoFileFoundReturnsDefault) {
+  EXPECT_TRUE(provider_->Init());
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_oobe_enabled());
+}
+
+TEST_F(UmRealConfigProviderTest, DontReadStatefulInNormalMode) {
+  fake_hardware_.SetIsNormalBootMode(true);
+  WriteStatefulConfig("is_oobe_enabled=false");
+
+  EXPECT_TRUE(provider_->Init());
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_oobe_enabled());
+}
+
+TEST_F(UmRealConfigProviderTest, ReadStatefulInDevMode) {
+  fake_hardware_.SetIsNormalBootMode(false);
+  WriteRootfsConfig("is_oobe_enabled=true");
+  // Since the stateful is present, this should read that one.
+  WriteStatefulConfig("is_oobe_enabled=false");
+
+  EXPECT_TRUE(provider_->Init());
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_oobe_enabled());
+}
+
+TEST_F(UmRealConfigProviderTest, ReadRootfsIfStatefulNotFound) {
+  fake_hardware_.SetIsNormalBootMode(false);
+  WriteRootfsConfig("is_oobe_enabled=false");
+
+  EXPECT_TRUE(provider_->Init());
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_oobe_enabled());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_device_policy_provider.cc b/update_manager/real_device_policy_provider.cc
new file mode 100644
index 0000000..0abd9f7
--- /dev/null
+++ b/update_manager/real_device_policy_provider.cc
@@ -0,0 +1,187 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_device_policy_provider.h"
+
+#include <stdint.h>
+
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/time/time.h>
+#include <policy/device_policy.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/generic_variables.h"
+#include "update_engine/update_manager/real_shill_provider.h"
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using policy::DevicePolicy;
+using std::set;
+using std::string;
+
+namespace {
+
+const int kDevicePolicyRefreshRateInMinutes = 60;
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+RealDevicePolicyProvider::~RealDevicePolicyProvider() {
+  MessageLoop::current()->CancelTask(scheduled_refresh_);
+}
+
+bool RealDevicePolicyProvider::Init() {
+  CHECK(policy_provider_ != nullptr);
+
+  // On Init() we try to get the device policy and keep updating it.
+  RefreshDevicePolicyAndReschedule();
+
+  // We also listen for signals from the session manager to force a device
+  // policy refresh.
+  session_manager_proxy_->RegisterPropertyChangeCompleteSignalHandler(
+      base::Bind(&RealDevicePolicyProvider::OnPropertyChangedCompletedSignal,
+                 base::Unretained(this)),
+      base::Bind(&RealDevicePolicyProvider::OnSignalConnected,
+                 base::Unretained(this)));
+  return true;
+}
+
+void RealDevicePolicyProvider::OnPropertyChangedCompletedSignal(
+    const string& success) {
+  if (success != "success") {
+    LOG(WARNING) << "Received device policy updated signal with a failure.";
+  }
+  // We refresh the policy file even if the payload string is kSignalFailure.
+  LOG(INFO) << "Reloading and re-scheduling device policy due to signal "
+               "received.";
+  MessageLoop::current()->CancelTask(scheduled_refresh_);
+  scheduled_refresh_ = MessageLoop::kTaskIdNull;
+  RefreshDevicePolicyAndReschedule();
+}
+
+void RealDevicePolicyProvider::OnSignalConnected(const string& interface_name,
+                                                 const string& signal_name,
+                                                 bool successful) {
+  if (!successful) {
+    LOG(WARNING) << "We couldn't connect to SessionManager signal for updates "
+                    "on the device policy blob. We will reload the policy file "
+                    "periodically.";
+  }
+  // We do a one-time refresh of the DevicePolicy just in case we missed a
+  // signal between the first refresh and the time the signal handler was
+  // actually connected.
+  RefreshDevicePolicy();
+}
+
+void RealDevicePolicyProvider::RefreshDevicePolicyAndReschedule() {
+  RefreshDevicePolicy();
+  scheduled_refresh_ = MessageLoop::current()->PostDelayedTask(
+      FROM_HERE,
+      base::Bind(&RealDevicePolicyProvider::RefreshDevicePolicyAndReschedule,
+                 base::Unretained(this)),
+      TimeDelta::FromMinutes(kDevicePolicyRefreshRateInMinutes));
+}
+
+template<typename T>
+void RealDevicePolicyProvider::UpdateVariable(
+    AsyncCopyVariable<T>* var,
+    bool (DevicePolicy::*getter_method)(T*) const) {
+  T new_value;
+  if (policy_provider_->device_policy_is_loaded() &&
+      (policy_provider_->GetDevicePolicy().*getter_method)(&new_value)) {
+    var->SetValue(new_value);
+  } else {
+    var->UnsetValue();
+  }
+}
+
+template<typename T>
+void RealDevicePolicyProvider::UpdateVariable(
+    AsyncCopyVariable<T>* var,
+    bool (RealDevicePolicyProvider::*getter_method)(T*) const) {
+  T new_value;
+  if (policy_provider_->device_policy_is_loaded() &&
+      (this->*getter_method)(&new_value)) {
+    var->SetValue(new_value);
+  } else {
+    var->UnsetValue();
+  }
+}
+
+bool RealDevicePolicyProvider::ConvertAllowedConnectionTypesForUpdate(
+      set<ConnectionType>* allowed_types) const {
+  set<string> allowed_types_str;
+  if (!policy_provider_->GetDevicePolicy()
+      .GetAllowedConnectionTypesForUpdate(&allowed_types_str)) {
+    return false;
+  }
+  allowed_types->clear();
+  for (auto& type_str : allowed_types_str) {
+    ConnectionType type =
+        RealShillProvider::ParseConnectionType(type_str.c_str());
+    if (type != ConnectionType::kUnknown) {
+      allowed_types->insert(type);
+    } else {
+      LOG(WARNING) << "Policy includes unknown connection type: " << type_str;
+    }
+  }
+  return true;
+}
+
+bool RealDevicePolicyProvider::ConvertScatterFactor(
+    TimeDelta* scatter_factor) const {
+  int64_t scatter_factor_in_seconds;
+  if (!policy_provider_->GetDevicePolicy().GetScatterFactorInSeconds(
+      &scatter_factor_in_seconds)) {
+    return false;
+  }
+  if (scatter_factor_in_seconds < 0) {
+    LOG(WARNING) << "Ignoring negative scatter factor: "
+                 << scatter_factor_in_seconds;
+    return false;
+  }
+  *scatter_factor = TimeDelta::FromSeconds(scatter_factor_in_seconds);
+  return true;
+}
+
+void RealDevicePolicyProvider::RefreshDevicePolicy() {
+  if (!policy_provider_->Reload()) {
+    LOG(INFO) << "No device policies/settings present.";
+  }
+
+  var_device_policy_is_loaded_.SetValue(
+      policy_provider_->device_policy_is_loaded());
+
+  UpdateVariable(&var_release_channel_, &DevicePolicy::GetReleaseChannel);
+  UpdateVariable(&var_release_channel_delegated_,
+                 &DevicePolicy::GetReleaseChannelDelegated);
+  UpdateVariable(&var_update_disabled_, &DevicePolicy::GetUpdateDisabled);
+  UpdateVariable(&var_target_version_prefix_,
+                 &DevicePolicy::GetTargetVersionPrefix);
+  UpdateVariable(&var_scatter_factor_,
+                 &RealDevicePolicyProvider::ConvertScatterFactor);
+  UpdateVariable(
+      &var_allowed_connection_types_for_update_,
+      &RealDevicePolicyProvider::ConvertAllowedConnectionTypesForUpdate);
+  UpdateVariable(&var_owner_, &DevicePolicy::GetOwner);
+  UpdateVariable(&var_http_downloads_enabled_,
+                 &DevicePolicy::GetHttpDownloadsEnabled);
+  UpdateVariable(&var_au_p2p_enabled_, &DevicePolicy::GetAuP2PEnabled);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_device_policy_provider.h b/update_manager/real_device_policy_provider.h
new file mode 100644
index 0000000..6094e93
--- /dev/null
+++ b/update_manager/real_device_policy_provider.h
@@ -0,0 +1,166 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_DEVICE_POLICY_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_DEVICE_POLICY_PROVIDER_H_
+
+#include <set>
+#include <string>
+
+#include <brillo/message_loops/message_loop.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+#include <policy/libpolicy.h>
+#include <session_manager/dbus-proxies.h>
+
+#include "update_engine/update_manager/device_policy_provider.h"
+#include "update_engine/update_manager/generic_variables.h"
+
+namespace chromeos_update_manager {
+
+// DevicePolicyProvider concrete implementation.
+class RealDevicePolicyProvider : public DevicePolicyProvider {
+ public:
+  RealDevicePolicyProvider(org::chromium::SessionManagerInterfaceProxyInterface*
+                               session_manager_proxy,
+                           policy::PolicyProvider* policy_provider)
+      : policy_provider_(policy_provider),
+        session_manager_proxy_(session_manager_proxy) {}
+  ~RealDevicePolicyProvider();
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+  Variable<bool>* var_device_policy_is_loaded() override {
+    return &var_device_policy_is_loaded_;
+  }
+
+  Variable<std::string>* var_release_channel() override {
+    return &var_release_channel_;
+  }
+
+  Variable<bool>* var_release_channel_delegated() override {
+    return &var_release_channel_delegated_;
+  }
+
+  Variable<bool>* var_update_disabled() override {
+    return &var_update_disabled_;
+  }
+
+  Variable<std::string>* var_target_version_prefix() override {
+    return &var_target_version_prefix_;
+  }
+
+  Variable<base::TimeDelta>* var_scatter_factor() override {
+    return &var_scatter_factor_;
+  }
+
+  Variable<std::set<ConnectionType>>*
+      var_allowed_connection_types_for_update() override {
+    return &var_allowed_connection_types_for_update_;
+  }
+
+  Variable<std::string>* var_owner() override {
+    return &var_owner_;
+  }
+
+  Variable<bool>* var_http_downloads_enabled() override {
+    return &var_http_downloads_enabled_;
+  }
+
+  Variable<bool>* var_au_p2p_enabled() override {
+    return &var_au_p2p_enabled_;
+  }
+
+ private:
+  FRIEND_TEST(UmRealDevicePolicyProviderTest, RefreshScheduledTest);
+  FRIEND_TEST(UmRealDevicePolicyProviderTest, NonExistentDevicePolicyReloaded);
+  FRIEND_TEST(UmRealDevicePolicyProviderTest, ValuesUpdated);
+
+  // A static handler for the PropertyChangedCompleted signal from the session
+  // manager used as a callback.
+  void OnPropertyChangedCompletedSignal(const std::string& success);
+
+  // Called when the signal in UpdateEngineLibcrosProxyResolvedInterface is
+  // connected.
+  void OnSignalConnected(const std::string& interface_name,
+                         const std::string& signal_name,
+                         bool successful);
+
+  // Schedules a call to periodically refresh the device policy.
+  void RefreshDevicePolicyAndReschedule();
+
+  // Reloads the device policy and updates all the exposed variables.
+  void RefreshDevicePolicy();
+
+  // Updates the async variable |var| based on the result value of the method
+  // passed, which is a DevicePolicy getter method.
+  template<typename T>
+  void UpdateVariable(AsyncCopyVariable<T>* var,
+                      bool (policy::DevicePolicy::*getter_method)(T*) const);
+
+  // Updates the async variable |var| based on the result value of the getter
+  // method passed, which is a wrapper getter on this class.
+  template<typename T>
+  void UpdateVariable(
+      AsyncCopyVariable<T>* var,
+      bool (RealDevicePolicyProvider::*getter_method)(T*) const);
+
+  // Wrapper for DevicePolicy::GetScatterFactorInSeconds() that converts the
+  // result to a base::TimeDelta. It returns the same value as
+  // GetScatterFactorInSeconds().
+  bool ConvertScatterFactor(base::TimeDelta* scatter_factor) const;
+
+  // Wrapper for DevicePolicy::GetAllowedConnectionTypesForUpdate() that
+  // converts the result to a set of ConnectionType elements instead of strings.
+  bool ConvertAllowedConnectionTypesForUpdate(
+      std::set<ConnectionType>* allowed_types) const;
+
+  // Used for fetching information about the device policy.
+  policy::PolicyProvider* policy_provider_;
+
+  // Used to schedule refreshes of the device policy.
+  brillo::MessageLoop::TaskId scheduled_refresh_{
+      brillo::MessageLoop::kTaskIdNull};
+
+  // The DBus (mockable) session manager proxy, owned by the caller.
+  org::chromium::SessionManagerInterfaceProxyInterface* session_manager_proxy_{
+      nullptr};
+
+  // Variable exposing whether the policy is loaded.
+  AsyncCopyVariable<bool> var_device_policy_is_loaded_{
+      "policy_is_loaded", false};
+
+  // Variables mapping the exposed methods from the policy::DevicePolicy.
+  AsyncCopyVariable<std::string> var_release_channel_{"release_channel"};
+  AsyncCopyVariable<bool> var_release_channel_delegated_{
+      "release_channel_delegated"};
+  AsyncCopyVariable<bool> var_update_disabled_{"update_disabled"};
+  AsyncCopyVariable<std::string> var_target_version_prefix_{
+      "target_version_prefix"};
+  AsyncCopyVariable<base::TimeDelta> var_scatter_factor_{"scatter_factor"};
+  AsyncCopyVariable<std::set<ConnectionType>>
+      var_allowed_connection_types_for_update_{
+          "allowed_connection_types_for_update"};
+  AsyncCopyVariable<std::string> var_owner_{"owner"};
+  AsyncCopyVariable<bool> var_http_downloads_enabled_{"http_downloads_enabled"};
+  AsyncCopyVariable<bool> var_au_p2p_enabled_{"au_p2p_enabled"};
+
+  DISALLOW_COPY_AND_ASSIGN(RealDevicePolicyProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_DEVICE_POLICY_PROVIDER_H_
diff --git a/update_manager/real_device_policy_provider_unittest.cc b/update_manager/real_device_policy_provider_unittest.cc
new file mode 100644
index 0000000..c480b60
--- /dev/null
+++ b/update_manager/real_device_policy_provider_unittest.cc
@@ -0,0 +1,227 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_device_policy_provider.h"
+
+#include <memory>
+
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <policy/mock_device_policy.h>
+#include <policy/mock_libpolicy.h>
+#include <session_manager/dbus-proxies.h>
+#include <session_manager/dbus-proxy-mocks.h>
+
+#include "update_engine/common/test_utils.h"
+#include "update_engine/dbus_test_utils.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using chromeos_update_engine::dbus_test_utils::MockSignalHandler;
+using std::set;
+using std::string;
+using std::unique_ptr;
+using testing::DoAll;
+using testing::Mock;
+using testing::Return;
+using testing::ReturnRef;
+using testing::SetArgPointee;
+using testing::_;
+
+namespace chromeos_update_manager {
+
+class UmRealDevicePolicyProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    provider_.reset(new RealDevicePolicyProvider(&session_manager_proxy_mock_,
+                                                 &mock_policy_provider_));
+    // By default, we have a device policy loaded. Tests can call
+    // SetUpNonExistentDevicePolicy() to override this.
+    SetUpExistentDevicePolicy();
+
+    // Setup the session manager_proxy such that it will accept the signal
+    // handler and store it in the |property_change_complete_| once registered.
+    MOCK_SIGNAL_HANDLER_EXPECT_SIGNAL_HANDLER(property_change_complete_,
+                                              session_manager_proxy_mock_,
+                                              PropertyChangeComplete);
+  }
+
+  void TearDown() override {
+    provider_.reset();
+    // Check for leaked callbacks on the main loop.
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  void SetUpNonExistentDevicePolicy() {
+    ON_CALL(mock_policy_provider_, Reload())
+        .WillByDefault(Return(false));
+    ON_CALL(mock_policy_provider_, device_policy_is_loaded())
+        .WillByDefault(Return(false));
+    EXPECT_CALL(mock_policy_provider_, GetDevicePolicy()).Times(0);
+  }
+
+  void SetUpExistentDevicePolicy() {
+    // Setup the default behavior of the mocked PolicyProvider.
+    ON_CALL(mock_policy_provider_, Reload())
+        .WillByDefault(Return(true));
+    ON_CALL(mock_policy_provider_, device_policy_is_loaded())
+        .WillByDefault(Return(true));
+    ON_CALL(mock_policy_provider_, GetDevicePolicy())
+        .WillByDefault(ReturnRef(mock_device_policy_));
+  }
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  org::chromium::SessionManagerInterfaceProxyMock session_manager_proxy_mock_;
+  testing::NiceMock<policy::MockDevicePolicy> mock_device_policy_;
+  testing::NiceMock<policy::MockPolicyProvider> mock_policy_provider_;
+  unique_ptr<RealDevicePolicyProvider> provider_;
+
+  // The registered signal handler for the signal.
+  MockSignalHandler<void(const string&)> property_change_complete_;
+};
+
+TEST_F(UmRealDevicePolicyProviderTest, RefreshScheduledTest) {
+  // Check that the RefreshPolicy gets scheduled by checking the TaskId.
+  EXPECT_TRUE(provider_->Init());
+  EXPECT_NE(MessageLoop::kTaskIdNull, provider_->scheduled_refresh_);
+  loop_.RunOnce(false);
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, FirstReload) {
+  // Checks that the policy is reloaded and the DevicePolicy is consulted twice:
+  // once on Init() and once again when the signal is connected.
+  EXPECT_CALL(mock_policy_provider_, Reload());
+  EXPECT_TRUE(provider_->Init());
+  Mock::VerifyAndClearExpectations(&mock_policy_provider_);
+
+  EXPECT_CALL(mock_policy_provider_, Reload());
+  loop_.RunOnce(false);
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, NonExistentDevicePolicyReloaded) {
+  // Checks that the policy is reloaded by RefreshDevicePolicy().
+  SetUpNonExistentDevicePolicy();
+  EXPECT_CALL(mock_policy_provider_, Reload()).Times(3);
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+  // Force the policy refresh.
+  provider_->RefreshDevicePolicy();
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, SessionManagerSignalForcesReload) {
+  // Checks that a signal from the SessionManager forces a reload.
+  SetUpNonExistentDevicePolicy();
+  EXPECT_CALL(mock_policy_provider_, Reload()).Times(2);
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+  Mock::VerifyAndClearExpectations(&mock_policy_provider_);
+
+  EXPECT_CALL(mock_policy_provider_, Reload());
+  ASSERT_TRUE(property_change_complete_.IsHandlerRegistered());
+  property_change_complete_.signal_callback().Run("success");
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, NonExistentDevicePolicyEmptyVariables) {
+  SetUpNonExistentDevicePolicy();
+  EXPECT_CALL(mock_policy_provider_, GetDevicePolicy()).Times(0);
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+
+  UmTestUtils::ExpectVariableHasValue(false,
+                                      provider_->var_device_policy_is_loaded());
+
+  UmTestUtils::ExpectVariableNotSet(provider_->var_release_channel());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_release_channel_delegated());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_update_disabled());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_target_version_prefix());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_scatter_factor());
+  UmTestUtils::ExpectVariableNotSet(
+      provider_->var_allowed_connection_types_for_update());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_owner());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_http_downloads_enabled());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_au_p2p_enabled());
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, ValuesUpdated) {
+  SetUpNonExistentDevicePolicy();
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+  Mock::VerifyAndClearExpectations(&mock_policy_provider_);
+
+  // Reload the policy with a good one and set some values as present. The
+  // remaining values are false.
+  SetUpExistentDevicePolicy();
+  EXPECT_CALL(mock_device_policy_, GetReleaseChannel(_))
+      .WillOnce(DoAll(SetArgPointee<0>(string("mychannel")), Return(true)));
+  EXPECT_CALL(mock_device_policy_, GetAllowedConnectionTypesForUpdate(_))
+      .WillOnce(Return(false));
+
+  provider_->RefreshDevicePolicy();
+
+  UmTestUtils::ExpectVariableHasValue(true,
+                                      provider_->var_device_policy_is_loaded());
+
+  // Test that at least one variable is set, to ensure the refresh occurred.
+  UmTestUtils::ExpectVariableHasValue(string("mychannel"),
+                                      provider_->var_release_channel());
+  UmTestUtils::ExpectVariableNotSet(
+      provider_->var_allowed_connection_types_for_update());
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, ScatterFactorConverted) {
+  SetUpExistentDevicePolicy();
+  EXPECT_CALL(mock_device_policy_, GetScatterFactorInSeconds(_))
+      .Times(2)
+      .WillRepeatedly(DoAll(SetArgPointee<0>(1234), Return(true)));
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+
+  UmTestUtils::ExpectVariableHasValue(TimeDelta::FromSeconds(1234),
+                                      provider_->var_scatter_factor());
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, NegativeScatterFactorIgnored) {
+  SetUpExistentDevicePolicy();
+  EXPECT_CALL(mock_device_policy_, GetScatterFactorInSeconds(_))
+      .Times(2)
+      .WillRepeatedly(DoAll(SetArgPointee<0>(-1), Return(true)));
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+
+  UmTestUtils::ExpectVariableNotSet(provider_->var_scatter_factor());
+}
+
+TEST_F(UmRealDevicePolicyProviderTest, AllowedTypesConverted) {
+  SetUpExistentDevicePolicy();
+  EXPECT_CALL(mock_device_policy_, GetAllowedConnectionTypesForUpdate(_))
+      .Times(2)
+      .WillRepeatedly(DoAll(
+          SetArgPointee<0>(set<string>{"bluetooth", "wifi", "not-a-type"}),
+          Return(true)));
+  EXPECT_TRUE(provider_->Init());
+  loop_.RunOnce(false);
+
+  UmTestUtils::ExpectVariableHasValue(
+      set<ConnectionType>{ConnectionType::kWifi, ConnectionType::kBluetooth},
+      provider_->var_allowed_connection_types_for_update());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_random_provider.cc b/update_manager/real_random_provider.cc
new file mode 100644
index 0000000..ed0eb4d
--- /dev/null
+++ b/update_manager/real_random_provider.cc
@@ -0,0 +1,89 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_random_provider.h"
+
+#include <stdio.h>
+#include <unistd.h>
+
+#include <string>
+
+#include <base/files/file_path.h>
+#include <base/files/scoped_file.h>
+#include <base/strings/stringprintf.h>
+
+#include "update_engine/update_manager/variable.h"
+
+using std::string;
+
+namespace {
+
+// The device providing randomness.
+const char* kRandomDevice = "/dev/urandom";
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+// A random seed variable.
+class RandomSeedVariable : public Variable<uint64_t> {
+ public:
+  // RandomSeedVariable is initialized as kVariableModeConst to let the
+  // EvaluationContext cache the value between different evaluations of the same
+  // policy request.
+  RandomSeedVariable(const string& name, FILE* fp)
+      : Variable<uint64_t>(name, kVariableModeConst), fp_(fp) {}
+  ~RandomSeedVariable() override {}
+
+ protected:
+  const uint64_t* GetValue(base::TimeDelta /* timeout */,
+                           string* errmsg) override {
+    uint64_t result;
+    // Aliasing via char pointer abides by the C/C++ strict-aliasing rules.
+    char* const buf = reinterpret_cast<char*>(&result);
+    unsigned int buf_rd = 0;
+
+    while (buf_rd < sizeof(result)) {
+      int rd = fread(buf + buf_rd, 1, sizeof(result) - buf_rd, fp_.get());
+      if (rd == 0 || ferror(fp_.get())) {
+        // Either EOF on fp or read failed.
+        if (errmsg) {
+          *errmsg = base::StringPrintf(
+              "Error reading from the random device: %s", kRandomDevice);
+        }
+        return nullptr;
+      }
+      buf_rd += rd;
+    }
+
+    return new uint64_t(result);
+  }
+
+ private:
+  base::ScopedFILE fp_;
+
+  DISALLOW_COPY_AND_ASSIGN(RandomSeedVariable);
+};
+
+bool RealRandomProvider::Init(void) {
+  FILE* fp = fopen(kRandomDevice, "r");
+  if (!fp)
+    return false;
+  var_seed_.reset(new RandomSeedVariable("seed", fp));
+  return true;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_random_provider.h b/update_manager/real_random_provider.h
new file mode 100644
index 0000000..14ce7a3
--- /dev/null
+++ b/update_manager/real_random_provider.h
@@ -0,0 +1,45 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_RANDOM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_RANDOM_PROVIDER_H_
+
+#include <memory>
+
+#include "update_engine/update_manager/random_provider.h"
+
+namespace chromeos_update_manager {
+
+// RandomProvider implementation class.
+class RealRandomProvider : public RandomProvider {
+ public:
+  RealRandomProvider() {}
+
+  Variable<uint64_t>* var_seed() override { return var_seed_.get(); }
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+ private:
+  // The seed() scoped variable.
+  std::unique_ptr<Variable<uint64_t>> var_seed_;
+
+  DISALLOW_COPY_AND_ASSIGN(RealRandomProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_RANDOM_PROVIDER_H_
diff --git a/update_manager/real_random_provider_unittest.cc b/update_manager/real_random_provider_unittest.cc
new file mode 100644
index 0000000..ca67da6
--- /dev/null
+++ b/update_manager/real_random_provider_unittest.cc
@@ -0,0 +1,67 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_random_provider.h"
+
+#include <gtest/gtest.h>
+
+#include <memory>
+
+#include "update_engine/update_manager/umtest_utils.h"
+
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+class UmRealRandomProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    // The provider initializes correctly.
+    provider_.reset(new RealRandomProvider());
+    ASSERT_NE(nullptr, provider_.get());
+    ASSERT_TRUE(provider_->Init());
+
+    provider_->var_seed();
+  }
+
+  unique_ptr<RealRandomProvider> provider_;
+};
+
+TEST_F(UmRealRandomProviderTest, InitFinalize) {
+  // The provider initializes all variables with valid objects.
+  EXPECT_NE(nullptr, provider_->var_seed());
+}
+
+TEST_F(UmRealRandomProviderTest, GetRandomValues) {
+  // Should not return the same random seed repeatedly.
+  unique_ptr<const uint64_t> value(
+      provider_->var_seed()->GetValue(UmTestUtils::DefaultTimeout(), nullptr));
+  ASSERT_NE(nullptr, value.get());
+
+  // Test that at least the returned values are different. This test fails,
+  // by design, once every 2^320 runs.
+  bool is_same_value = true;
+  for (int i = 0; i < 5; i++) {
+    unique_ptr<const uint64_t> other_value(
+        provider_->var_seed()->GetValue(UmTestUtils::DefaultTimeout(),
+                                        nullptr));
+    ASSERT_NE(nullptr, other_value.get());
+    is_same_value = is_same_value && *other_value == *value;
+  }
+  EXPECT_FALSE(is_same_value);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_shill_provider.cc b/update_manager/real_shill_provider.cc
new file mode 100644
index 0000000..7938180
--- /dev/null
+++ b/update_manager/real_shill_provider.cc
@@ -0,0 +1,191 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_shill_provider.h"
+
+#include <string>
+
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
+#include <brillo/type_name_undecorate.h>
+#include <shill/dbus-constants.h>
+#include <shill/dbus-proxies.h>
+
+using org::chromium::flimflam::ManagerProxyInterface;
+using org::chromium::flimflam::ServiceProxyInterface;
+using std::string;
+
+namespace chromeos_update_manager {
+
+ConnectionType RealShillProvider::ParseConnectionType(const string& type_str) {
+  if (type_str == shill::kTypeEthernet) {
+    return ConnectionType::kEthernet;
+  } else if (type_str == shill::kTypeWifi) {
+    return ConnectionType::kWifi;
+  } else if (type_str == shill::kTypeWimax) {
+    return ConnectionType::kWimax;
+  } else if (type_str == shill::kTypeBluetooth) {
+    return ConnectionType::kBluetooth;
+  } else if (type_str == shill::kTypeCellular) {
+    return ConnectionType::kCellular;
+  }
+  return ConnectionType::kUnknown;
+}
+
+ConnectionTethering RealShillProvider::ParseConnectionTethering(
+    const string& tethering_str) {
+  if (tethering_str == shill::kTetheringNotDetectedState) {
+    return ConnectionTethering::kNotDetected;
+  } else if (tethering_str == shill::kTetheringSuspectedState) {
+    return ConnectionTethering::kSuspected;
+  } else if (tethering_str == shill::kTetheringConfirmedState) {
+    return ConnectionTethering::kConfirmed;
+  }
+  return ConnectionTethering::kUnknown;
+}
+
+bool RealShillProvider::Init() {
+  ManagerProxyInterface* manager_proxy = shill_proxy_->GetManagerProxy();
+  if (!manager_proxy)
+    return false;
+
+  // Subscribe to the manager's PropertyChanged signal.
+  manager_proxy->RegisterPropertyChangedSignalHandler(
+      base::Bind(&RealShillProvider::OnManagerPropertyChanged,
+                 base::Unretained(this)),
+      base::Bind(&RealShillProvider::OnSignalConnected,
+                 base::Unretained(this)));
+
+  // Attempt to read initial connection status. Even if this fails because shill
+  // is not responding (e.g. it is down) we'll be notified via "PropertyChanged"
+  // signal as soon as it comes up, so this is not a critical step.
+  brillo::VariantDictionary properties;
+  brillo::ErrorPtr error;
+  if (!manager_proxy->GetProperties(&properties, &error))
+    return true;
+
+  const auto& prop_default_service =
+      properties.find(shill::kDefaultServiceProperty);
+  if (prop_default_service != properties.end()) {
+    OnManagerPropertyChanged(prop_default_service->first,
+                             prop_default_service->second);
+  }
+
+  return true;
+}
+
+void RealShillProvider::OnManagerPropertyChanged(const string& name,
+                                                 const brillo::Any& value) {
+  if (name == shill::kDefaultServiceProperty) {
+    dbus::ObjectPath service_path = value.TryGet<dbus::ObjectPath>();
+    if (!service_path.IsValid()) {
+      LOG(WARNING) << "Got an invalid DefaultService path. The property value "
+                      "contains a "
+                   << value.GetUndecoratedTypeName()
+                   << ", read as the object path: '" << service_path.value()
+                   << "'";
+    }
+    ProcessDefaultService(service_path);
+  }
+}
+
+void RealShillProvider::OnSignalConnected(const string& interface_name,
+                                          const string& signal_name,
+                                          bool successful) {
+  if (!successful) {
+    LOG(ERROR) << "Couldn't connect to the signal " << interface_name << "."
+               << signal_name;
+  }
+}
+
+bool RealShillProvider::ProcessDefaultService(
+    const dbus::ObjectPath& default_service_path) {
+  // We assume that if the service path didn't change, then the connection
+  // type and the tethering status of it also didn't change.
+  if (default_service_path_ == default_service_path)
+    return true;
+
+  // Update the connection status.
+  default_service_path_ = default_service_path;
+  bool is_connected = (default_service_path_.IsValid() &&
+                       default_service_path_.value() != "/");
+  var_is_connected_.SetValue(is_connected);
+  var_conn_last_changed_.SetValue(clock_->GetWallclockTime());
+
+  if (!is_connected) {
+    var_conn_type_.UnsetValue();
+    var_conn_tethering_.UnsetValue();
+    return true;
+  }
+
+  // We create and dispose the ServiceProxyInterface on every request.
+  std::unique_ptr<ServiceProxyInterface> service =
+      shill_proxy_->GetServiceForPath(default_service_path_);
+
+  // Get the connection properties synchronously.
+  brillo::VariantDictionary properties;
+  brillo::ErrorPtr error;
+  if (!service->GetProperties(&properties, &error)) {
+    var_conn_type_.UnsetValue();
+    var_conn_tethering_.UnsetValue();
+    return false;
+  }
+
+  // Get the connection tethering mode.
+  const auto& prop_tethering = properties.find(shill::kTetheringProperty);
+  if (prop_tethering == properties.end()) {
+    // Remove the value if not present on the service. This most likely means an
+    // error in shill and the policy will handle it, but we will print a log
+    // message as well for accessing an unused variable.
+    var_conn_tethering_.UnsetValue();
+    LOG(ERROR) << "Could not find connection type (service: "
+               << default_service_path_.value() << ")";
+  } else {
+    // If the property doesn't contain a string value, the empty string will
+    // become kUnknown.
+    var_conn_tethering_.SetValue(
+        ParseConnectionTethering(prop_tethering->second.TryGet<string>()));
+  }
+
+  // Get the connection type.
+  const auto& prop_type = properties.find(shill::kTypeProperty);
+  if (prop_type == properties.end()) {
+    var_conn_type_.UnsetValue();
+    LOG(ERROR) << "Could not find connection tethering mode (service: "
+               << default_service_path_.value() << ")";
+  } else {
+    string type_str = prop_type->second.TryGet<string>();
+    if (type_str == shill::kTypeVPN) {
+      const auto& prop_physical =
+          properties.find(shill::kPhysicalTechnologyProperty);
+      if (prop_physical == properties.end()) {
+        LOG(ERROR) << "No PhysicalTechnology property found for a VPN"
+                   << " connection (service: " << default_service_path_.value()
+                   << "). Using default kUnknown value.";
+        var_conn_type_.SetValue(ConnectionType::kUnknown);
+      } else {
+        var_conn_type_.SetValue(
+            ParseConnectionType(prop_physical->second.TryGet<string>()));
+      }
+    } else {
+      var_conn_type_.SetValue(ParseConnectionType(type_str));
+    }
+  }
+
+  return true;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_shill_provider.h b/update_manager/real_shill_provider.h
new file mode 100644
index 0000000..dbd6fc5
--- /dev/null
+++ b/update_manager/real_shill_provider.h
@@ -0,0 +1,104 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_SHILL_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_SHILL_PROVIDER_H_
+
+// TODO(garnold) Much of the functionality in this module was adapted from the
+// update engine's connection_manager.  We need to make sure to deprecate use of
+// connection manager when the time comes.
+
+#include <string>
+
+#include <base/time/time.h>
+#include <dbus/object_path.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/shill_proxy_interface.h"
+#include "update_engine/update_manager/generic_variables.h"
+#include "update_engine/update_manager/shill_provider.h"
+
+namespace chromeos_update_manager {
+
+// ShillProvider concrete implementation.
+class RealShillProvider : public ShillProvider {
+ public:
+  RealShillProvider(chromeos_update_engine::ShillProxyInterface* shill_proxy,
+                    chromeos_update_engine::ClockInterface* clock)
+      : shill_proxy_(shill_proxy), clock_(clock) {}
+
+  ~RealShillProvider() override = default;
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+  Variable<bool>* var_is_connected() override {
+    return &var_is_connected_;
+  }
+
+  Variable<ConnectionType>* var_conn_type() override {
+    return &var_conn_type_;
+  }
+
+  Variable<ConnectionTethering>* var_conn_tethering() override {
+    return &var_conn_tethering_;
+  }
+
+  Variable<base::Time>* var_conn_last_changed() override {
+    return &var_conn_last_changed_;
+  }
+
+  // Helper methods for converting shill strings into symbolic values.
+  static ConnectionType ParseConnectionType(const std::string& type_str);
+  static ConnectionTethering ParseConnectionTethering(
+      const std::string& tethering_str);
+
+ private:
+  // A handler for ManagerProxy.PropertyChanged signal.
+  void OnManagerPropertyChanged(const std::string& name,
+                                const brillo::Any& value);
+
+  // Called when the signal in ManagerProxy.PropertyChanged is connected.
+  void OnSignalConnected(const std::string& interface_name,
+                         const std::string& signal_name,
+                         bool successful);
+
+  // Get the connection and populate the type and tethering status of the given
+  // default connection.
+  bool ProcessDefaultService(const dbus::ObjectPath& default_service_path);
+
+  // The current default service path, if connected. "/" means not connected.
+  dbus::ObjectPath default_service_path_{"uninitialized"};
+
+  // The mockable interface to access the shill DBus proxies, owned by the
+  // caller.
+  chromeos_update_engine::ShillProxyInterface* shill_proxy_;
+
+  // A clock abstraction (mockable).
+  chromeos_update_engine::ClockInterface* const clock_;
+
+  // The provider's variables.
+  AsyncCopyVariable<bool> var_is_connected_{"is_connected"};
+  AsyncCopyVariable<ConnectionType> var_conn_type_{"conn_type"};
+  AsyncCopyVariable<ConnectionTethering> var_conn_tethering_{"conn_tethering"};
+  AsyncCopyVariable<base::Time> var_conn_last_changed_{"conn_last_changed"};
+
+  DISALLOW_COPY_AND_ASSIGN(RealShillProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_SHILL_PROVIDER_H_
diff --git a/update_manager/real_shill_provider_unittest.cc b/update_manager/real_shill_provider_unittest.cc
new file mode 100644
index 0000000..2fa0628
--- /dev/null
+++ b/update_manager/real_shill_provider_unittest.cc
@@ -0,0 +1,530 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_shill_provider.h"
+
+#include <memory>
+#include <utility>
+
+#include <base/time/time.h>
+#include <brillo/make_unique_ptr.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <shill/dbus-constants.h>
+#include <shill/dbus-proxies.h>
+#include <shill/dbus-proxy-mocks.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/test_utils.h"
+#include "update_engine/dbus_test_utils.h"
+#include "update_engine/fake_shill_proxy.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::FakeClock;
+using org::chromium::flimflam::ManagerProxyMock;
+using org::chromium::flimflam::ServiceProxyMock;
+using std::unique_ptr;
+using testing::Mock;
+using testing::Return;
+using testing::SetArgPointee;
+using testing::_;
+
+namespace {
+
+// Fake service paths.
+const char* const kFakeEthernetServicePath = "/fake/ethernet/service";
+const char* const kFakeWifiServicePath = "/fake/wifi/service";
+const char* const kFakeWimaxServicePath = "/fake/wimax/service";
+const char* const kFakeBluetoothServicePath = "/fake/bluetooth/service";
+const char* const kFakeCellularServicePath = "/fake/cellular/service";
+const char* const kFakeVpnServicePath = "/fake/vpn/service";
+const char* const kFakeUnknownServicePath = "/fake/unknown/service";
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+class UmRealShillProviderTest : public ::testing::Test {
+ protected:
+  // Initialize the RealShillProvider under test.
+  void SetUp() override {
+    fake_clock_.SetWallclockTime(InitTime());
+    loop_.SetAsCurrent();
+    provider_.reset(new RealShillProvider(&fake_shill_proxy_, &fake_clock_));
+
+    ManagerProxyMock* manager_proxy_mock = fake_shill_proxy_.GetManagerProxy();
+
+    // The PropertyChanged signal should be subscribed to.
+    MOCK_SIGNAL_HANDLER_EXPECT_SIGNAL_HANDLER(
+        manager_property_changed_, *manager_proxy_mock, PropertyChanged);
+  }
+
+  void TearDown() override {
+    provider_.reset();
+    // Check for leaked callbacks on the main loop.
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  // These methods generate fixed timestamps for use in faking the current time.
+  Time InitTime() {
+    Time::Exploded now_exp;
+    now_exp.year = 2014;
+    now_exp.month = 3;
+    now_exp.day_of_week = 2;
+    now_exp.day_of_month = 18;
+    now_exp.hour = 8;
+    now_exp.minute = 5;
+    now_exp.second = 33;
+    now_exp.millisecond = 675;
+    return Time::FromLocalExploded(now_exp);
+  }
+
+  Time ConnChangedTime() {
+    return InitTime() + TimeDelta::FromSeconds(10);
+  }
+
+  // Sets the default_service object path in the response from the
+  // ManagerProxyMock instance.
+  void SetManagerReply(const char* default_service, bool reply_succeeds);
+
+  // Sets the |service_type|, |physical_technology| and |service_tethering|
+  // properties in the mocked service |service_path|. If any of the three
+  // const char* is a nullptr, the corresponding property will not be included
+  // in the response.
+  // Returns the mock object pointer, owned by the |fake_shill_proxy_|.
+  ServiceProxyMock* SetServiceReply(const std::string& service_path,
+                                    const char* service_type,
+                                    const char* physical_technology,
+                                    const char* service_tethering);
+
+  void InitWithDefaultService(const char* default_service) {
+    SetManagerReply(default_service, true);
+    // Check that provider initializes correctly.
+    EXPECT_TRUE(provider_->Init());
+    // RunOnce to notify the signal handler was connected properly.
+    EXPECT_TRUE(loop_.RunOnce(false));
+  }
+
+  // Sends a signal informing the provider about a default connection
+  // |service_path|. Sets the fake connection change time in
+  // |conn_change_time_p| if provided.
+  void SendDefaultServiceSignal(const std::string& service_path,
+                                Time* conn_change_time_p) {
+    const Time conn_change_time = ConnChangedTime();
+    fake_clock_.SetWallclockTime(conn_change_time);
+    ASSERT_TRUE(manager_property_changed_.IsHandlerRegistered());
+    manager_property_changed_.signal_callback().Run(
+        shill::kDefaultServiceProperty, dbus::ObjectPath(service_path));
+    fake_clock_.SetWallclockTime(conn_change_time + TimeDelta::FromSeconds(5));
+    if (conn_change_time_p)
+      *conn_change_time_p = conn_change_time;
+  }
+
+  // Sets up expectations for detection of a connection |service_path| with type
+  // |shill_type_str| and tethering mode |shill_tethering_str|. Ensures that the
+  // new connection status and change time are properly detected by the
+  // provider. Writes the fake connection change time to |conn_change_time_p|,
+  // if provided.
+  void SetupConnectionAndAttrs(const std::string& service_path,
+                               const char* shill_type,
+                               const char* shill_tethering,
+                               Time* conn_change_time_p) {
+    SetServiceReply(service_path, shill_type, nullptr, shill_tethering);
+    // Note: We don't setup this |service_path| as the default service path but
+    // we instead send a signal notifying the change since the code won't call
+    // GetProperties on the Manager object at this point.
+
+    // Send a signal about a new default service.
+    Time conn_change_time;
+    SendDefaultServiceSignal(service_path, &conn_change_time);
+
+    // Query the connection status, ensure last change time reported correctly.
+    UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_connected());
+    UmTestUtils::ExpectVariableHasValue(conn_change_time,
+                                        provider_->var_conn_last_changed());
+
+    // Write the connection change time to the output argument.
+    if (conn_change_time_p)
+      *conn_change_time_p = conn_change_time;
+  }
+
+  // Sets up a connection and tests that its type is being properly detected by
+  // the provider.
+  void SetupConnectionAndTestType(const char* service_path,
+                                  const char* shill_type,
+                                  ConnectionType expected_conn_type) {
+    // Set up and test the connection, record the change time.
+    Time conn_change_time;
+    SetupConnectionAndAttrs(service_path,
+                            shill_type,
+                            shill::kTetheringNotDetectedState,
+                            &conn_change_time);
+
+    // Query the connection type, ensure last change time did not change.
+    UmTestUtils::ExpectVariableHasValue(expected_conn_type,
+                                        provider_->var_conn_type());
+    UmTestUtils::ExpectVariableHasValue(conn_change_time,
+                                        provider_->var_conn_last_changed());
+  }
+
+  // Sets up a connection and tests that its tethering mode is being properly
+  // detected by the provider.
+  void SetupConnectionAndTestTethering(
+      const char* service_path,
+      const char* shill_tethering,
+      ConnectionTethering expected_conn_tethering) {
+    // Set up and test the connection, record the change time.
+    Time conn_change_time;
+    SetupConnectionAndAttrs(
+        service_path, shill::kTypeEthernet, shill_tethering, &conn_change_time);
+
+    // Query the connection tethering, ensure last change time did not change.
+    UmTestUtils::ExpectVariableHasValue(expected_conn_tethering,
+                                        provider_->var_conn_tethering());
+    UmTestUtils::ExpectVariableHasValue(conn_change_time,
+                                        provider_->var_conn_last_changed());
+  }
+
+  brillo::FakeMessageLoop loop_{nullptr};
+  FakeClock fake_clock_;
+  chromeos_update_engine::FakeShillProxy fake_shill_proxy_;
+
+  // The registered signal handler for the signal Manager.PropertyChanged.
+  chromeos_update_engine::dbus_test_utils::MockSignalHandler<
+      void(const std::string&, const brillo::Any&)> manager_property_changed_;
+
+  unique_ptr<RealShillProvider> provider_;
+};
+
+void UmRealShillProviderTest::SetManagerReply(const char* default_service,
+                                              bool reply_succeeds) {
+  ManagerProxyMock* manager_proxy_mock = fake_shill_proxy_.GetManagerProxy();
+  if (!reply_succeeds) {
+    EXPECT_CALL(*manager_proxy_mock, GetProperties(_, _, _))
+        .WillOnce(Return(false));
+    return;
+  }
+
+  // Create a dictionary of properties and optionally include the default
+  // service.
+  brillo::VariantDictionary reply_dict;
+  reply_dict["SomeOtherProperty"] = 0xC0FFEE;
+
+  if (default_service) {
+    reply_dict[shill::kDefaultServiceProperty] =
+        dbus::ObjectPath(default_service);
+  }
+  EXPECT_CALL(*manager_proxy_mock, GetProperties(_, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(reply_dict), Return(true)));
+}
+
+ServiceProxyMock* UmRealShillProviderTest::SetServiceReply(
+    const std::string& service_path,
+    const char* service_type,
+    const char* physical_technology,
+    const char* service_tethering) {
+  brillo::VariantDictionary reply_dict;
+  reply_dict["SomeOtherProperty"] = 0xC0FFEE;
+
+  if (service_type)
+    reply_dict[shill::kTypeProperty] = std::string(service_type);
+
+  if (physical_technology) {
+    reply_dict[shill::kPhysicalTechnologyProperty] =
+        std::string(physical_technology);
+  }
+
+  if (service_tethering)
+    reply_dict[shill::kTetheringProperty] = std::string(service_tethering);
+
+  ServiceProxyMock* service_proxy_mock = new ServiceProxyMock();
+
+  // Plumb return value into mock object.
+  EXPECT_CALL(*service_proxy_mock, GetProperties(_, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(reply_dict), Return(true)));
+
+  fake_shill_proxy_.SetServiceForPath(
+      dbus::ObjectPath(service_path),
+      brillo::make_unique_ptr(service_proxy_mock));
+  return service_proxy_mock;
+}
+
+
+// Query the connection status, type and time last changed, as they were set
+// during initialization (no signals).
+TEST_F(UmRealShillProviderTest, ReadBaseValues) {
+  InitWithDefaultService("/");
+  // Query the provider variables.
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_connected());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_conn_type());
+  UmTestUtils::ExpectVariableHasValue(InitTime(),
+                                      provider_->var_conn_last_changed());
+}
+
+// Ensure that invalid DBus paths are ignored.
+TEST_F(UmRealShillProviderTest, InvalidServicePath) {
+  InitWithDefaultService("invalid");
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_connected());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_conn_type());
+  UmTestUtils::ExpectVariableHasValue(InitTime(),
+                                      provider_->var_conn_last_changed());
+}
+
+// Ensure that a service path property including a different type is ignored.
+TEST_F(UmRealShillProviderTest, InvalidServicePathType) {
+  ManagerProxyMock* manager_proxy_mock = fake_shill_proxy_.GetManagerProxy();
+  brillo::VariantDictionary reply_dict;
+  reply_dict[shill::kDefaultServiceProperty] = "/not/an/object/path";
+  EXPECT_CALL(*manager_proxy_mock, GetProperties(_, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(reply_dict), Return(true)));
+
+  EXPECT_TRUE(provider_->Init());
+  EXPECT_TRUE(loop_.RunOnce(false));
+
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_connected());
+}
+
+// Test that Ethernet connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeEthernet) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeEthernetServicePath,
+                             shill::kTypeEthernet,
+                             ConnectionType::kEthernet);
+}
+
+// Test that Wifi connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeWifi) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeWifiServicePath,
+                             shill::kTypeWifi,
+                             ConnectionType::kWifi);
+}
+
+// Test that Wimax connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeWimax) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeWimaxServicePath,
+                             shill::kTypeWimax,
+                             ConnectionType::kWimax);
+}
+
+// Test that Bluetooth connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeBluetooth) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeBluetoothServicePath,
+                             shill::kTypeBluetooth,
+                             ConnectionType::kBluetooth);
+}
+
+// Test that Cellular connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeCellular) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeCellularServicePath,
+                             shill::kTypeCellular,
+                             ConnectionType::kCellular);
+}
+
+// Test that an unknown connection is identified as such.
+TEST_F(UmRealShillProviderTest, ReadConnTypeUnknown) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeUnknownServicePath,
+                             "FooConnectionType",
+                             ConnectionType::kUnknown);
+}
+
+// Tests that VPN connection is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTypeVpn) {
+  InitWithDefaultService("/");
+  // Mock logic for returning a default service path and its type.
+  SetServiceReply(kFakeVpnServicePath,
+                  shill::kTypeVPN,
+                  shill::kTypeWifi,
+                  shill::kTetheringNotDetectedState);
+
+  // Send a signal about a new default service.
+  Time conn_change_time;
+  SendDefaultServiceSignal(kFakeVpnServicePath, &conn_change_time);
+
+  // Query the connection type, ensure last change time reported correctly.
+  UmTestUtils::ExpectVariableHasValue(ConnectionType::kWifi,
+                                      provider_->var_conn_type());
+  UmTestUtils::ExpectVariableHasValue(conn_change_time,
+                                      provider_->var_conn_last_changed());
+}
+
+// Ensure that the connection type is properly cached in the provider through
+// subsequent variable readings.
+TEST_F(UmRealShillProviderTest, ConnTypeCacheUsed) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeEthernetServicePath,
+                             shill::kTypeEthernet,
+                             ConnectionType::kEthernet);
+
+  UmTestUtils::ExpectVariableHasValue(ConnectionType::kEthernet,
+                                      provider_->var_conn_type());
+}
+
+// Ensure that the cached connection type remains valid even when a default
+// connection signal occurs but the connection is not changed.
+TEST_F(UmRealShillProviderTest, ConnTypeCacheRemainsValid) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeEthernetServicePath,
+                             shill::kTypeEthernet,
+                             ConnectionType::kEthernet);
+
+  SendDefaultServiceSignal(kFakeEthernetServicePath, nullptr);
+
+  UmTestUtils::ExpectVariableHasValue(ConnectionType::kEthernet,
+                                      provider_->var_conn_type());
+}
+
+// Ensure that the cached connection type is invalidated and re-read when the
+// default connection changes.
+TEST_F(UmRealShillProviderTest, ConnTypeCacheInvalidated) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestType(kFakeEthernetServicePath,
+                             shill::kTypeEthernet,
+                             ConnectionType::kEthernet);
+
+  SetupConnectionAndTestType(kFakeWifiServicePath,
+                             shill::kTypeWifi,
+                             ConnectionType::kWifi);
+}
+
+// Test that a non-tethering mode is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTetheringNotDetected) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeWifiServicePath,
+                                  shill::kTetheringNotDetectedState,
+                                  ConnectionTethering::kNotDetected);
+}
+
+// Test that a suspected tethering mode is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTetheringSuspected) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeWifiServicePath,
+                                  shill::kTetheringSuspectedState,
+                                  ConnectionTethering::kSuspected);
+}
+
+// Test that a confirmed tethering mode is identified correctly.
+TEST_F(UmRealShillProviderTest, ReadConnTetheringConfirmed) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeWifiServicePath,
+                                  shill::kTetheringConfirmedState,
+                                  ConnectionTethering::kConfirmed);
+}
+
+// Test that an unknown tethering mode is identified as such.
+TEST_F(UmRealShillProviderTest, ReadConnTetheringUnknown) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeWifiServicePath,
+                                  "FooConnTethering",
+                                  ConnectionTethering::kUnknown);
+}
+
+// Ensure that the connection tethering mode is properly cached in the provider.
+TEST_F(UmRealShillProviderTest, ConnTetheringCacheUsed) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeEthernetServicePath,
+                                  shill::kTetheringNotDetectedState,
+                                  ConnectionTethering::kNotDetected);
+
+  UmTestUtils::ExpectVariableHasValue(ConnectionTethering::kNotDetected,
+                                      provider_->var_conn_tethering());
+}
+
+// Ensure that the cached connection tethering mode remains valid even when a
+// default connection signal occurs but the connection is not changed.
+TEST_F(UmRealShillProviderTest, ConnTetheringCacheRemainsValid) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeEthernetServicePath,
+                                  shill::kTetheringNotDetectedState,
+                                  ConnectionTethering::kNotDetected);
+
+  SendDefaultServiceSignal(kFakeEthernetServicePath, nullptr);
+
+  UmTestUtils::ExpectVariableHasValue(ConnectionTethering::kNotDetected,
+                                      provider_->var_conn_tethering());
+}
+
+// Ensure that the cached connection tethering mode is invalidated and re-read
+// when the default connection changes.
+TEST_F(UmRealShillProviderTest, ConnTetheringCacheInvalidated) {
+  InitWithDefaultService("/");
+  SetupConnectionAndTestTethering(kFakeEthernetServicePath,
+                                  shill::kTetheringNotDetectedState,
+                                  ConnectionTethering::kNotDetected);
+
+  SetupConnectionAndTestTethering(kFakeWifiServicePath,
+                                  shill::kTetheringConfirmedState,
+                                  ConnectionTethering::kConfirmed);
+}
+
+// Fake two DBus signals prompting a default connection change, but otherwise
+// give the same service path. Check connection status and the time it was last
+// changed, making sure that it is the time when the first signal was sent (and
+// not the second).
+TEST_F(UmRealShillProviderTest, ReadLastChangedTimeTwoSignals) {
+  InitWithDefaultService("/");
+  // Send a default service signal twice, advancing the clock in between.
+  Time conn_change_time;
+  SetupConnectionAndAttrs(kFakeEthernetServicePath,
+                          shill::kTypeEthernet,
+                          shill::kTetheringNotDetectedState,
+                          &conn_change_time);
+  // This will set the service path to the same value, so it should not call
+  // GetProperties() again.
+  SendDefaultServiceSignal(kFakeEthernetServicePath, nullptr);
+
+  // Query the connection status, ensure last change time reported as the first
+  // time the signal was sent.
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_connected());
+  UmTestUtils::ExpectVariableHasValue(conn_change_time,
+                                      provider_->var_conn_last_changed());
+}
+
+// Make sure that the provider initializes correctly even if shill is not
+// responding, that variables can be obtained, and that they all return a null
+// value (indicating that the underlying values were not set).
+TEST_F(UmRealShillProviderTest, NoInitConnStatusReadBaseValues) {
+  // Initialize the provider, no initial connection status response.
+  SetManagerReply(nullptr, false);
+  EXPECT_TRUE(provider_->Init());
+  EXPECT_TRUE(loop_.RunOnce(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_is_connected());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_conn_type());
+  UmTestUtils::ExpectVariableNotSet(provider_->var_conn_last_changed());
+}
+
+// Test that, once a signal is received, the connection status and other info
+// can be read correctly.
+TEST_F(UmRealShillProviderTest, NoInitConnStatusReadConnTypeEthernet) {
+  // Initialize the provider with no initial connection status response.
+  SetManagerReply(nullptr, false);
+  EXPECT_TRUE(provider_->Init());
+  EXPECT_TRUE(loop_.RunOnce(false));
+
+  SetupConnectionAndAttrs(kFakeEthernetServicePath,
+                          shill::kTypeEthernet,
+                          shill::kTetheringNotDetectedState,
+                          nullptr);
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_connected());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_state.h b/update_manager/real_state.h
new file mode 100644
index 0000000..e83c49d
--- /dev/null
+++ b/update_manager/real_state.h
@@ -0,0 +1,82 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_STATE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_STATE_H_
+
+#include <memory>
+
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+// State concrete implementation.
+class RealState : public State {
+ public:
+  ~RealState() override {}
+
+  RealState(ConfigProvider* config_provider,
+            DevicePolicyProvider* device_policy_provider,
+            RandomProvider* random_provider,
+            ShillProvider* shill_provider,
+            SystemProvider* system_provider,
+            TimeProvider* time_provider,
+            UpdaterProvider* updater_provider) :
+      config_provider_(config_provider),
+      device_policy_provider_(device_policy_provider),
+      random_provider_(random_provider),
+      shill_provider_(shill_provider),
+      system_provider_(system_provider),
+      time_provider_(time_provider),
+      updater_provider_(updater_provider) {}
+
+  // These methods return the given provider.
+  ConfigProvider* config_provider() override {
+    return config_provider_.get();
+  }
+  DevicePolicyProvider* device_policy_provider() override {
+    return device_policy_provider_.get();
+  }
+  RandomProvider* random_provider() override {
+    return random_provider_.get();
+  }
+  ShillProvider* shill_provider() override {
+    return shill_provider_.get();
+  }
+  SystemProvider* system_provider() override {
+    return system_provider_.get();
+  }
+  TimeProvider* time_provider() override {
+    return time_provider_.get();
+  }
+  UpdaterProvider* updater_provider() override {
+    return updater_provider_.get();
+  }
+
+ private:
+  // Instances of the providers.
+  std::unique_ptr<ConfigProvider> config_provider_;
+  std::unique_ptr<DevicePolicyProvider> device_policy_provider_;
+  std::unique_ptr<RandomProvider> random_provider_;
+  std::unique_ptr<ShillProvider> shill_provider_;
+  std::unique_ptr<SystemProvider> system_provider_;
+  std::unique_ptr<TimeProvider> time_provider_;
+  std::unique_ptr<UpdaterProvider> updater_provider_;
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_STATE_H_
diff --git a/update_manager/real_system_provider.cc b/update_manager/real_system_provider.cc
new file mode 100644
index 0000000..040f37c
--- /dev/null
+++ b/update_manager/real_system_provider.cc
@@ -0,0 +1,60 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_system_provider.h"
+
+#include <string.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/utils.h"
+#include "update_engine/update_manager/generic_variables.h"
+
+using std::string;
+
+namespace chromeos_update_manager {
+
+bool RealSystemProvider::Init() {
+  var_is_normal_boot_mode_.reset(
+      new ConstCopyVariable<bool>("is_normal_boot_mode",
+                                  hardware_->IsNormalBootMode()));
+
+  var_is_official_build_.reset(
+      new ConstCopyVariable<bool>("is_official_build",
+                                  hardware_->IsOfficialBuild()));
+
+  var_is_oobe_complete_.reset(
+      new CallCopyVariable<bool>(
+          "is_oobe_complete",
+          base::Bind(&chromeos_update_engine::HardwareInterface::IsOOBEComplete,
+                     base::Unretained(hardware_), nullptr)));
+
+  var_num_slots_.reset(
+      new ConstCopyVariable<unsigned int>(
+          "num_slots", boot_control_->GetNumSlots()));
+
+  return true;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_system_provider.h b/update_manager/real_system_provider.h
new file mode 100644
index 0000000..0329d74
--- /dev/null
+++ b/update_manager/real_system_provider.h
@@ -0,0 +1,70 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_SYSTEM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_SYSTEM_PROVIDER_H_
+
+#include <memory>
+#include <string>
+
+#include "update_engine/common/boot_control_interface.h"
+#include "update_engine/common/hardware_interface.h"
+#include "update_engine/update_manager/system_provider.h"
+
+namespace chromeos_update_manager {
+
+// SystemProvider concrete implementation.
+class RealSystemProvider : public SystemProvider {
+ public:
+  explicit RealSystemProvider(
+      chromeos_update_engine::HardwareInterface* hardware,
+      chromeos_update_engine::BootControlInterface* boot_control)
+      : hardware_(hardware), boot_control_(boot_control) {}
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+  Variable<bool>* var_is_normal_boot_mode() override {
+    return var_is_normal_boot_mode_.get();
+  }
+
+  Variable<bool>* var_is_official_build() override {
+    return var_is_official_build_.get();
+  }
+
+  Variable<bool>* var_is_oobe_complete() override {
+    return var_is_oobe_complete_.get();
+  }
+
+  Variable<unsigned int>* var_num_slots() override {
+    return var_num_slots_.get();
+  }
+
+ private:
+  std::unique_ptr<Variable<bool>> var_is_normal_boot_mode_;
+  std::unique_ptr<Variable<bool>> var_is_official_build_;
+  std::unique_ptr<Variable<bool>> var_is_oobe_complete_;
+  std::unique_ptr<Variable<unsigned int>> var_num_slots_;
+
+  chromeos_update_engine::HardwareInterface* hardware_;
+  chromeos_update_engine::BootControlInterface* boot_control_;
+
+  DISALLOW_COPY_AND_ASSIGN(RealSystemProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_SYSTEM_PROVIDER_H_
diff --git a/update_manager/real_system_provider_unittest.cc b/update_manager/real_system_provider_unittest.cc
new file mode 100644
index 0000000..5ee4137
--- /dev/null
+++ b/update_manager/real_system_provider_unittest.cc
@@ -0,0 +1,61 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_system_provider.h"
+
+#include <memory>
+
+#include <base/time/time.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_boot_control.h"
+#include "update_engine/common/fake_hardware.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+class UmRealSystemProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    provider_.reset(
+        new RealSystemProvider(&fake_hardware_, &fake_boot_control_));
+    EXPECT_TRUE(provider_->Init());
+  }
+
+  chromeos_update_engine::FakeHardware fake_hardware_;
+  chromeos_update_engine::FakeBootControl fake_boot_control_;
+  unique_ptr<RealSystemProvider> provider_;
+};
+
+TEST_F(UmRealSystemProviderTest, InitTest) {
+  EXPECT_NE(nullptr, provider_->var_is_normal_boot_mode());
+  EXPECT_NE(nullptr, provider_->var_is_official_build());
+  EXPECT_NE(nullptr, provider_->var_is_oobe_complete());
+}
+
+TEST_F(UmRealSystemProviderTest, IsOOBECompleteTrue) {
+  fake_hardware_.SetIsOOBEComplete(base::Time());
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_is_oobe_complete());
+}
+
+TEST_F(UmRealSystemProviderTest, IsOOBECompleteFalse) {
+  fake_hardware_.UnsetIsOOBEComplete();
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_is_oobe_complete());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_time_provider.cc b/update_manager/real_time_provider.cc
new file mode 100644
index 0000000..ca3acad
--- /dev/null
+++ b/update_manager/real_time_provider.cc
@@ -0,0 +1,83 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_time_provider.h"
+
+#include <string>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/clock_interface.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::ClockInterface;
+using std::string;
+
+namespace chromeos_update_manager {
+
+// A variable returning the current date.
+class CurrDateVariable : public Variable<Time> {
+ public:
+  // TODO(garnold) Turn this into an async variable with the needed callback
+  // logic for when it value changes.
+  CurrDateVariable(const string& name, ClockInterface* clock)
+      : Variable<Time>(name, TimeDelta::FromHours(1)), clock_(clock) {}
+
+ protected:
+  virtual const Time* GetValue(TimeDelta /* timeout */,
+                               string* /* errmsg */) {
+    Time::Exploded now_exp;
+    clock_->GetWallclockTime().LocalExplode(&now_exp);
+    now_exp.hour = now_exp.minute = now_exp.second = now_exp.millisecond = 0;
+    return new Time(Time::FromLocalExploded(now_exp));
+  }
+
+ private:
+  ClockInterface* clock_;
+
+  DISALLOW_COPY_AND_ASSIGN(CurrDateVariable);
+};
+
+// A variable returning the current hour in local time.
+class CurrHourVariable : public Variable<int> {
+ public:
+  // TODO(garnold) Turn this into an async variable with the needed callback
+  // logic for when it value changes.
+  CurrHourVariable(const string& name, ClockInterface* clock)
+      : Variable<int>(name, TimeDelta::FromMinutes(5)), clock_(clock) {}
+
+ protected:
+  virtual const int* GetValue(TimeDelta /* timeout */,
+                              string* /* errmsg */) {
+    Time::Exploded exploded;
+    clock_->GetWallclockTime().LocalExplode(&exploded);
+    return new int(exploded.hour);
+  }
+
+ private:
+  ClockInterface* clock_;
+
+  DISALLOW_COPY_AND_ASSIGN(CurrHourVariable);
+};
+
+bool RealTimeProvider::Init() {
+  var_curr_date_.reset(new CurrDateVariable("curr_date", clock_));
+  var_curr_hour_.reset(new CurrHourVariable("curr_hour", clock_));
+  return true;
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_time_provider.h b/update_manager/real_time_provider.h
new file mode 100644
index 0000000..e7cae94
--- /dev/null
+++ b/update_manager/real_time_provider.h
@@ -0,0 +1,58 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_TIME_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_TIME_PROVIDER_H_
+
+#include <memory>
+
+#include <base/time/time.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/update_manager/time_provider.h"
+
+namespace chromeos_update_manager {
+
+// TimeProvider concrete implementation.
+class RealTimeProvider : public TimeProvider {
+ public:
+  explicit RealTimeProvider(chromeos_update_engine::ClockInterface* clock)
+      : clock_(clock) {}
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init();
+
+  Variable<base::Time>* var_curr_date() override {
+    return var_curr_date_.get();
+  }
+
+  Variable<int>* var_curr_hour() override {
+    return var_curr_hour_.get();
+  }
+
+ private:
+  // A clock abstraction (fakeable).
+  chromeos_update_engine::ClockInterface* const clock_;
+
+  std::unique_ptr<Variable<base::Time>> var_curr_date_;
+  std::unique_ptr<Variable<int>> var_curr_hour_;
+
+  DISALLOW_COPY_AND_ASSIGN(RealTimeProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_TIME_PROVIDER_H_
diff --git a/update_manager/real_time_provider_unittest.cc b/update_manager/real_time_provider_unittest.cc
new file mode 100644
index 0000000..0e1ef34
--- /dev/null
+++ b/update_manager/real_time_provider_unittest.cc
@@ -0,0 +1,84 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_time_provider.h"
+
+#include <memory>
+
+#include <base/logging.h>
+#include <base/time/time.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Time;
+using chromeos_update_engine::FakeClock;
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+class UmRealTimeProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    // The provider initializes correctly.
+    provider_.reset(new RealTimeProvider(&fake_clock_));
+    ASSERT_NE(nullptr, provider_.get());
+    ASSERT_TRUE(provider_->Init());
+  }
+
+  // Generates a fixed timestamp for use in faking the current time.
+  Time CurrTime() {
+    Time::Exploded now_exp;
+    now_exp.year = 2014;
+    now_exp.month = 3;
+    now_exp.day_of_week = 2;
+    now_exp.day_of_month = 18;
+    now_exp.hour = 8;
+    now_exp.minute = 5;
+    now_exp.second = 33;
+    now_exp.millisecond = 675;
+    return Time::FromLocalExploded(now_exp);
+  }
+
+  FakeClock fake_clock_;
+  unique_ptr<RealTimeProvider> provider_;
+};
+
+TEST_F(UmRealTimeProviderTest, CurrDateValid) {
+  const Time now = CurrTime();
+  Time::Exploded exploded;
+  now.LocalExplode(&exploded);
+  exploded.hour = 0;
+  exploded.minute = 0;
+  exploded.second = 0;
+  exploded.millisecond = 0;
+  const Time expected = Time::FromLocalExploded(exploded);
+
+  fake_clock_.SetWallclockTime(now);
+  UmTestUtils::ExpectVariableHasValue(expected, provider_->var_curr_date());
+}
+
+TEST_F(UmRealTimeProviderTest, CurrHourValid) {
+  const Time now = CurrTime();
+  Time::Exploded expected;
+  now.LocalExplode(&expected);
+  fake_clock_.SetWallclockTime(now);
+  UmTestUtils::ExpectVariableHasValue(expected.hour,
+                                      provider_->var_curr_hour());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_updater_provider.cc b/update_manager/real_updater_provider.cc
new file mode 100644
index 0000000..1a3e65a
--- /dev/null
+++ b/update_manager/real_updater_provider.cc
@@ -0,0 +1,453 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_updater_provider.h"
+
+#include <inttypes.h>
+
+#include <string>
+
+#include <base/bind.h>
+#include <base/strings/stringprintf.h>
+#include <base/time/time.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/common/prefs.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/update_attempter.h"
+
+using base::StringPrintf;
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::OmahaRequestParams;
+using chromeos_update_engine::SystemState;
+using std::string;
+
+namespace chromeos_update_manager {
+
+// A templated base class for all update related variables. Provides uniform
+// construction and a system state handle.
+template<typename T>
+class UpdaterVariableBase : public Variable<T> {
+ public:
+  UpdaterVariableBase(const string& name, VariableMode mode,
+                      SystemState* system_state)
+      : Variable<T>(name, mode), system_state_(system_state) {}
+
+ protected:
+  // The system state used for pulling information from the updater.
+  inline SystemState* system_state() const { return system_state_; }
+
+ private:
+  SystemState* const system_state_;
+};
+
+// Helper class for issuing a GetStatus() to the UpdateAttempter.
+class GetStatusHelper {
+ public:
+  GetStatusHelper(SystemState* system_state, string* errmsg) {
+    is_success_ = system_state->update_attempter()->GetStatus(
+        &last_checked_time_, &progress_, &update_status_, &new_version_,
+        &payload_size_);
+    if (!is_success_ && errmsg)
+      *errmsg = "Failed to get a status update from the update engine";
+  }
+
+  inline bool is_success() { return is_success_; }
+  inline int64_t last_checked_time() { return last_checked_time_; }
+  inline double progress() { return progress_; }
+  inline const string& update_status() { return update_status_; }
+  inline const string& new_version() { return new_version_; }
+  inline int64_t payload_size() { return payload_size_; }
+
+ private:
+  bool is_success_;
+  int64_t last_checked_time_;
+  double progress_;
+  string update_status_;
+  string new_version_;
+  int64_t payload_size_;
+};
+
+// A variable reporting the time when a last update check was issued.
+class LastCheckedTimeVariable : public UpdaterVariableBase<Time> {
+ public:
+  LastCheckedTimeVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<Time>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const Time* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    GetStatusHelper raw(system_state(), errmsg);
+    if (!raw.is_success())
+      return nullptr;
+
+    return new Time(Time::FromTimeT(raw.last_checked_time()));
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(LastCheckedTimeVariable);
+};
+
+// A variable reporting the update (download) progress as a decimal fraction
+// between 0.0 and 1.0.
+class ProgressVariable : public UpdaterVariableBase<double> {
+ public:
+  ProgressVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<double>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const double* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    GetStatusHelper raw(system_state(), errmsg);
+    if (!raw.is_success())
+      return nullptr;
+
+    if (raw.progress() < 0.0 || raw.progress() > 1.0) {
+      if (errmsg) {
+        *errmsg = StringPrintf("Invalid progress value received: %f",
+                               raw.progress());
+      }
+      return nullptr;
+    }
+
+    return new double(raw.progress());
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(ProgressVariable);
+};
+
+// A variable reporting the stage in which the update process is.
+class StageVariable : public UpdaterVariableBase<Stage> {
+ public:
+  StageVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<Stage>(name, kVariableModePoll, system_state) {}
+
+ private:
+  struct CurrOpStrToStage {
+    const char* str;
+    Stage stage;
+  };
+  static const CurrOpStrToStage curr_op_str_to_stage[];
+
+  // Note: the method is defined outside the class so arraysize can work.
+  const Stage* GetValue(TimeDelta /* timeout */, string* errmsg) override;
+
+  DISALLOW_COPY_AND_ASSIGN(StageVariable);
+};
+
+const StageVariable::CurrOpStrToStage StageVariable::curr_op_str_to_stage[] = {
+  {update_engine::kUpdateStatusIdle, Stage::kIdle},
+  {update_engine::kUpdateStatusCheckingForUpdate, Stage::kCheckingForUpdate},
+  {update_engine::kUpdateStatusUpdateAvailable, Stage::kUpdateAvailable},
+  {update_engine::kUpdateStatusDownloading, Stage::kDownloading},
+  {update_engine::kUpdateStatusVerifying, Stage::kVerifying},
+  {update_engine::kUpdateStatusFinalizing, Stage::kFinalizing},
+  {update_engine::kUpdateStatusUpdatedNeedReboot, Stage::kUpdatedNeedReboot},
+  {  // NOLINT(whitespace/braces)
+    update_engine::kUpdateStatusReportingErrorEvent,
+    Stage::kReportingErrorEvent
+  },
+  {update_engine::kUpdateStatusAttemptingRollback, Stage::kAttemptingRollback},
+};
+
+const Stage* StageVariable::GetValue(TimeDelta /* timeout */,
+                                     string* errmsg) {
+  GetStatusHelper raw(system_state(), errmsg);
+  if (!raw.is_success())
+    return nullptr;
+
+  for (auto& key_val : curr_op_str_to_stage)
+    if (raw.update_status() == key_val.str)
+      return new Stage(key_val.stage);
+
+  if (errmsg)
+    *errmsg = string("Unknown update status: ") + raw.update_status();
+  return nullptr;
+}
+
+// A variable reporting the version number that an update is updating to.
+class NewVersionVariable : public UpdaterVariableBase<string> {
+ public:
+  NewVersionVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<string>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const string* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    GetStatusHelper raw(system_state(), errmsg);
+    if (!raw.is_success())
+      return nullptr;
+
+    return new string(raw.new_version());
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(NewVersionVariable);
+};
+
+// A variable reporting the size of the update being processed in bytes.
+class PayloadSizeVariable : public UpdaterVariableBase<int64_t> {
+ public:
+  PayloadSizeVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<int64_t>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const int64_t* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    GetStatusHelper raw(system_state(), errmsg);
+    if (!raw.is_success())
+      return nullptr;
+
+    if (raw.payload_size() < 0) {
+      if (errmsg)
+        *errmsg = string("Invalid payload size: %" PRId64, raw.payload_size());
+      return nullptr;
+    }
+
+    return new int64_t(raw.payload_size());
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(PayloadSizeVariable);
+};
+
+// A variable reporting the point in time an update last completed in the
+// current boot cycle.
+//
+// TODO(garnold) In general, both the current boottime and wallclock time
+// readings should come from the time provider and be moderated by the
+// evaluation context, so that they are uniform throughout the evaluation of a
+// policy request.
+class UpdateCompletedTimeVariable : public UpdaterVariableBase<Time> {
+ public:
+  UpdateCompletedTimeVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<Time>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const Time* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    Time update_boottime;
+    if (!system_state()->update_attempter()->GetBootTimeAtUpdate(
+            &update_boottime)) {
+      if (errmsg)
+        *errmsg = "Update completed time could not be read";
+      return nullptr;
+    }
+
+    chromeos_update_engine::ClockInterface* clock = system_state()->clock();
+    Time curr_boottime = clock->GetBootTime();
+    if (curr_boottime < update_boottime) {
+      if (errmsg)
+        *errmsg = "Update completed time more recent than current time";
+      return nullptr;
+    }
+    TimeDelta duration_since_update = curr_boottime - update_boottime;
+    return new Time(clock->GetWallclockTime() - duration_since_update);
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateCompletedTimeVariable);
+};
+
+// Variables reporting the current image channel.
+class CurrChannelVariable : public UpdaterVariableBase<string> {
+ public:
+  CurrChannelVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<string>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const string* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    OmahaRequestParams* request_params = system_state()->request_params();
+    string channel = request_params->current_channel();
+    if (channel.empty()) {
+      if (errmsg)
+        *errmsg = "No current channel";
+      return nullptr;
+    }
+    return new string(channel);
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(CurrChannelVariable);
+};
+
+// Variables reporting the new image channel.
+class NewChannelVariable : public UpdaterVariableBase<string> {
+ public:
+  NewChannelVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<string>(name, kVariableModePoll, system_state) {}
+
+ private:
+  const string* GetValue(TimeDelta /* timeout */, string* errmsg) override {
+    OmahaRequestParams* request_params = system_state()->request_params();
+    string channel = request_params->target_channel();
+    if (channel.empty()) {
+      if (errmsg)
+        *errmsg = "No new channel";
+      return nullptr;
+    }
+    return new string(channel);
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(NewChannelVariable);
+};
+
+// A variable class for reading Boolean prefs values.
+class BooleanPrefVariable
+    : public AsyncCopyVariable<bool>,
+      public chromeos_update_engine::PrefsInterface::ObserverInterface {
+ public:
+  BooleanPrefVariable(const string& name,
+                      chromeos_update_engine::PrefsInterface* prefs,
+                      const char* key,
+                      bool default_val)
+      : AsyncCopyVariable<bool>(name),
+        prefs_(prefs),
+        key_(key),
+        default_val_(default_val) {
+    prefs->AddObserver(key, this);
+    OnPrefSet(key);
+  }
+  ~BooleanPrefVariable() {
+    prefs_->RemoveObserver(key_, this);
+  }
+
+ private:
+  // Reads the actual value from the Prefs instance and updates the Variable
+  // value.
+  void OnPrefSet(const string& key) override {
+    bool result = default_val_;
+    if (prefs_ && prefs_->Exists(key_) && !prefs_->GetBoolean(key_, &result))
+      result = default_val_;
+    // AsyncCopyVariable will take care of values that didn't change.
+    SetValue(result);
+  }
+
+  void OnPrefDeleted(const string& key) override {
+    SetValue(default_val_);
+  }
+
+  chromeos_update_engine::PrefsInterface* prefs_;
+
+  // The Boolean preference key and default value.
+  const char* const key_;
+  const bool default_val_;
+
+  DISALLOW_COPY_AND_ASSIGN(BooleanPrefVariable);
+};
+
+// A variable returning the number of consecutive failed update checks.
+class ConsecutiveFailedUpdateChecksVariable
+    : public UpdaterVariableBase<unsigned int> {
+ public:
+  ConsecutiveFailedUpdateChecksVariable(const string& name,
+                                        SystemState* system_state)
+      : UpdaterVariableBase<unsigned int>(name, kVariableModePoll,
+                                          system_state) {}
+
+ private:
+  const unsigned int* GetValue(TimeDelta /* timeout */,
+                               string* /* errmsg */) override {
+    return new unsigned int(
+        system_state()->update_attempter()->consecutive_failed_update_checks());
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(ConsecutiveFailedUpdateChecksVariable);
+};
+
+// A variable returning the server-dictated poll interval.
+class ServerDictatedPollIntervalVariable
+    : public UpdaterVariableBase<unsigned int> {
+ public:
+  ServerDictatedPollIntervalVariable(const string& name,
+                                     SystemState* system_state)
+      : UpdaterVariableBase<unsigned int>(name, kVariableModePoll,
+                                          system_state) {}
+
+ private:
+  const unsigned int* GetValue(TimeDelta /* timeout */,
+                               string* /* errmsg */) override {
+    return new unsigned int(
+        system_state()->update_attempter()->server_dictated_poll_interval());
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(ServerDictatedPollIntervalVariable);
+};
+
+// An async variable that tracks changes to forced update requests.
+class ForcedUpdateRequestedVariable
+    : public UpdaterVariableBase<UpdateRequestStatus> {
+ public:
+  ForcedUpdateRequestedVariable(const string& name, SystemState* system_state)
+      : UpdaterVariableBase<UpdateRequestStatus>::UpdaterVariableBase(
+          name, kVariableModeAsync, system_state) {
+    system_state->update_attempter()->set_forced_update_pending_callback(
+        new base::Callback<void(bool, bool)>(  // NOLINT(readability/function)
+            base::Bind(&ForcedUpdateRequestedVariable::Reset,
+                       base::Unretained(this))));
+  }
+
+ private:
+  const UpdateRequestStatus* GetValue(TimeDelta /* timeout */,
+                                      string* /* errmsg */) override {
+    return new UpdateRequestStatus(update_request_status_);
+  }
+
+  void Reset(bool forced_update_requested, bool is_interactive) {
+    UpdateRequestStatus new_value = UpdateRequestStatus::kNone;
+    if (forced_update_requested)
+      new_value = (is_interactive ? UpdateRequestStatus::kInteractive :
+                   UpdateRequestStatus::kPeriodic);
+    if (update_request_status_ != new_value) {
+      update_request_status_ = new_value;
+      NotifyValueChanged();
+    }
+  }
+
+  UpdateRequestStatus update_request_status_ = UpdateRequestStatus::kNone;
+
+  DISALLOW_COPY_AND_ASSIGN(ForcedUpdateRequestedVariable);
+};
+
+// RealUpdaterProvider methods.
+
+RealUpdaterProvider::RealUpdaterProvider(SystemState* system_state)
+  : system_state_(system_state),
+    var_updater_started_time_("updater_started_time",
+                              system_state->clock()->GetWallclockTime()),
+    var_last_checked_time_(
+        new LastCheckedTimeVariable("last_checked_time", system_state_)),
+    var_update_completed_time_(
+        new UpdateCompletedTimeVariable("update_completed_time",
+                                        system_state_)),
+    var_progress_(new ProgressVariable("progress", system_state_)),
+    var_stage_(new StageVariable("stage", system_state_)),
+    var_new_version_(new NewVersionVariable("new_version", system_state_)),
+    var_payload_size_(new PayloadSizeVariable("payload_size", system_state_)),
+    var_curr_channel_(new CurrChannelVariable("curr_channel", system_state_)),
+    var_new_channel_(new NewChannelVariable("new_channel", system_state_)),
+    var_p2p_enabled_(
+        new BooleanPrefVariable("p2p_enabled", system_state_->prefs(),
+                                chromeos_update_engine::kPrefsP2PEnabled,
+                                false)),
+    var_cellular_enabled_(
+        new BooleanPrefVariable(
+            "cellular_enabled", system_state_->prefs(),
+            chromeos_update_engine::kPrefsUpdateOverCellularPermission,
+            false)),
+    var_consecutive_failed_update_checks_(
+        new ConsecutiveFailedUpdateChecksVariable(
+            "consecutive_failed_update_checks", system_state_)),
+    var_server_dictated_poll_interval_(
+        new ServerDictatedPollIntervalVariable(
+            "server_dictated_poll_interval", system_state_)),
+    var_forced_update_requested_(
+        new ForcedUpdateRequestedVariable(
+            "forced_update_requested", system_state_)) {}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/real_updater_provider.h b/update_manager/real_updater_provider.h
new file mode 100644
index 0000000..b99bcc5
--- /dev/null
+++ b/update_manager/real_updater_provider.h
@@ -0,0 +1,124 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_REAL_UPDATER_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_REAL_UPDATER_PROVIDER_H_
+
+#include <memory>
+#include <string>
+
+#include "update_engine/system_state.h"
+#include "update_engine/update_manager/generic_variables.h"
+#include "update_engine/update_manager/updater_provider.h"
+
+namespace chromeos_update_manager {
+
+// A concrete UpdaterProvider implementation using local (in-process) bindings.
+class RealUpdaterProvider : public UpdaterProvider {
+ public:
+  // We assume that any other object handle we get from the system state is
+  // "volatile", and so must be re-acquired whenever access is needed; this
+  // guarantees that parts of the system state can be mocked out at any time
+  // during testing. We further assume that, by the time Init() is called, the
+  // system state object is fully populated and usable.
+  explicit RealUpdaterProvider(
+      chromeos_update_engine::SystemState* system_state);
+
+  // Initializes the provider and returns whether it succeeded.
+  bool Init() { return true; }
+
+  Variable<base::Time>* var_updater_started_time() override {
+    return &var_updater_started_time_;
+  }
+
+  Variable<base::Time>* var_last_checked_time() override {
+    return var_last_checked_time_.get();
+  }
+
+  Variable<base::Time>* var_update_completed_time() override {
+    return var_update_completed_time_.get();
+  }
+
+  Variable<double>* var_progress() override {
+    return var_progress_.get();
+  }
+
+  Variable<Stage>* var_stage() override {
+    return var_stage_.get();
+  }
+
+  Variable<std::string>* var_new_version() override {
+    return var_new_version_.get();
+  }
+
+  Variable<int64_t>* var_payload_size() override {
+    return var_payload_size_.get();
+  }
+
+  Variable<std::string>* var_curr_channel() override {
+    return var_curr_channel_.get();
+  }
+
+  Variable<std::string>* var_new_channel() override {
+    return var_new_channel_.get();
+  }
+
+  Variable<bool>* var_p2p_enabled() override {
+    return var_p2p_enabled_.get();
+  }
+
+  Variable<bool>* var_cellular_enabled() override {
+    return var_cellular_enabled_.get();
+  }
+
+  Variable<unsigned int>* var_consecutive_failed_update_checks() override {
+    return var_consecutive_failed_update_checks_.get();
+  }
+
+  Variable<unsigned int>* var_server_dictated_poll_interval() override {
+    return var_server_dictated_poll_interval_.get();
+  }
+
+  Variable<UpdateRequestStatus>* var_forced_update_requested() override {
+    return var_forced_update_requested_.get();
+  }
+
+ private:
+  // A pointer to the update engine's system state aggregator.
+  chromeos_update_engine::SystemState* system_state_;
+
+  // Variable implementations.
+  ConstCopyVariable<base::Time> var_updater_started_time_;
+  std::unique_ptr<Variable<base::Time>> var_last_checked_time_;
+  std::unique_ptr<Variable<base::Time>> var_update_completed_time_;
+  std::unique_ptr<Variable<double>> var_progress_;
+  std::unique_ptr<Variable<Stage>> var_stage_;
+  std::unique_ptr<Variable<std::string>> var_new_version_;
+  std::unique_ptr<Variable<int64_t>> var_payload_size_;
+  std::unique_ptr<Variable<std::string>> var_curr_channel_;
+  std::unique_ptr<Variable<std::string>> var_new_channel_;
+  std::unique_ptr<Variable<bool>> var_p2p_enabled_;
+  std::unique_ptr<Variable<bool>> var_cellular_enabled_;
+  std::unique_ptr<Variable<unsigned int>> var_consecutive_failed_update_checks_;
+  std::unique_ptr<Variable<unsigned int>> var_server_dictated_poll_interval_;
+  std::unique_ptr<Variable<UpdateRequestStatus>> var_forced_update_requested_;
+
+  DISALLOW_COPY_AND_ASSIGN(RealUpdaterProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_REAL_UPDATER_PROVIDER_H_
diff --git a/update_manager/real_updater_provider_unittest.cc b/update_manager/real_updater_provider_unittest.cc
new file mode 100644
index 0000000..14eb30b
--- /dev/null
+++ b/update_manager/real_updater_provider_unittest.cc
@@ -0,0 +1,443 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/real_updater_provider.h"
+
+#include <memory>
+#include <string>
+
+#include <base/time/time.h>
+#include <gtest/gtest.h>
+#include <update_engine/dbus-constants.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/common/fake_prefs.h"
+#include "update_engine/fake_system_state.h"
+#include "update_engine/mock_update_attempter.h"
+#include "update_engine/omaha_request_params.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Time;
+using base::TimeDelta;
+using chromeos_update_engine::FakeClock;
+using chromeos_update_engine::FakePrefs;
+using chromeos_update_engine::FakeSystemState;
+using chromeos_update_engine::OmahaRequestParams;
+using std::string;
+using std::unique_ptr;
+using testing::Return;
+using testing::SetArgPointee;
+using testing::_;
+
+namespace {
+
+// Generates a fixed timestamp for use in faking the current time.
+Time FixedTime() {
+  Time::Exploded now_exp;
+  now_exp.year = 2014;
+  now_exp.month = 3;
+  now_exp.day_of_week = 2;
+  now_exp.day_of_month = 18;
+  now_exp.hour = 8;
+  now_exp.minute = 5;
+  now_exp.second = 33;
+  now_exp.millisecond = 675;
+  return Time::FromLocalExploded(now_exp);
+}
+
+// Rounds down a timestamp to the nearest second. This is useful when faking
+// times that are converted to time_t (no sub-second resolution).
+Time RoundedToSecond(Time time) {
+  Time::Exploded exp;
+  time.LocalExplode(&exp);
+  exp.millisecond = 0;
+  return Time::FromLocalExploded(exp);
+}
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+class UmRealUpdaterProviderTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    fake_clock_ = fake_sys_state_.fake_clock();
+    fake_sys_state_.set_prefs(&fake_prefs_);
+    provider_.reset(new RealUpdaterProvider(&fake_sys_state_));
+    ASSERT_NE(nullptr, provider_.get());
+    // Check that provider initializes correctly.
+    ASSERT_TRUE(provider_->Init());
+  }
+
+  // Sets up mock expectations for testing the update completed time reporting.
+  // |valid| determines whether the returned time is valid. Returns the expected
+  // update completed time value.
+  Time SetupUpdateCompletedTime(bool valid) {
+    const TimeDelta kDurationSinceUpdate = TimeDelta::FromMinutes(7);
+    const Time kUpdateBootTime = Time() + kDurationSinceUpdate * 2;
+    const Time kCurrBootTime = (valid ?
+                                kUpdateBootTime + kDurationSinceUpdate :
+                                kUpdateBootTime - kDurationSinceUpdate);
+    const Time kCurrWallclockTime = FixedTime();
+    EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+                GetBootTimeAtUpdate(_))
+        .WillOnce(DoAll(SetArgPointee<0>(kUpdateBootTime), Return(true)));
+    fake_clock_->SetBootTime(kCurrBootTime);
+    fake_clock_->SetWallclockTime(kCurrWallclockTime);
+    return kCurrWallclockTime - kDurationSinceUpdate;
+  }
+
+  FakeSystemState fake_sys_state_;
+  FakeClock* fake_clock_;  // Short for fake_sys_state_.fake_clock()
+  FakePrefs fake_prefs_;
+  unique_ptr<RealUpdaterProvider> provider_;
+};
+
+TEST_F(UmRealUpdaterProviderTest, UpdaterStartedTimeIsWallclockTime) {
+  fake_clock_->SetWallclockTime(Time::FromDoubleT(123.456));
+  fake_clock_->SetMonotonicTime(Time::FromDoubleT(456.123));
+  // Run SetUp again to re-setup the provider under test to use these values.
+  SetUp();
+  UmTestUtils::ExpectVariableHasValue(Time::FromDoubleT(123.456),
+                                      provider_->var_updater_started_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetLastCheckedTimeOkay) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<0>(FixedTime().ToTimeT()), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(RoundedToSecond(FixedTime()),
+                                      provider_->var_last_checked_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetLastCheckedTimeFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_last_checked_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressOkayMin) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<1>(0.0), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(0.0, provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressOkayMid) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<1>(0.3), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(0.3, provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressOkayMax) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<1>(1.0), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(1.0, provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressFailTooSmall) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<1>(-2.0), Return(true)));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetProgressFailTooBig) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<1>(2.0), Return(true)));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_progress());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayIdle) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>(update_engine::kUpdateStatusIdle),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kIdle, provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayCheckingForUpdate) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<2>(update_engine::kUpdateStatusCheckingForUpdate),
+              Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kCheckingForUpdate,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayUpdateAvailable) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<2>(update_engine::kUpdateStatusUpdateAvailable),
+              Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kUpdateAvailable,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayDownloading) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>(update_engine::kUpdateStatusDownloading),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kDownloading,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayVerifying) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>(update_engine::kUpdateStatusVerifying),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kVerifying,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayFinalizing) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>(update_engine::kUpdateStatusFinalizing),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kFinalizing,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayUpdatedNeedReboot) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<2>(update_engine::kUpdateStatusUpdatedNeedReboot),
+              Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kUpdatedNeedReboot,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayReportingErrorEvent) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<2>(update_engine::kUpdateStatusReportingErrorEvent),
+              Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kReportingErrorEvent,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageOkayAttemptingRollback) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(
+              SetArgPointee<2>(update_engine::kUpdateStatusAttemptingRollback),
+              Return(true)));
+  UmTestUtils::ExpectVariableHasValue(Stage::kAttemptingRollback,
+                                      provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageFailUnknown) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>("FooUpdateEngineState"),
+                      Return(true)));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetStageFailEmpty) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<2>(""), Return(true)));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_stage());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetNewVersionOkay) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<3>("1.2.0"), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(string("1.2.0"),
+                                      provider_->var_new_version());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetNewVersionFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_new_version());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetPayloadSizeOkayZero) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<4>(static_cast<int64_t>(0)), Return(true)));
+  UmTestUtils::ExpectVariableHasValue(static_cast<int64_t>(0),
+                                      provider_->var_payload_size());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetPayloadSizeOkayArbitrary) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<4>(static_cast<int64_t>(567890)),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(static_cast<int64_t>(567890),
+                                      provider_->var_payload_size());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetPayloadSizeOkayTwoGigabytes) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<4>(static_cast<int64_t>(1) << 31),
+                      Return(true)));
+  UmTestUtils::ExpectVariableHasValue(static_cast<int64_t>(1) << 31,
+                                      provider_->var_payload_size());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetPayloadSizeFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_payload_size());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetPayloadSizeFailNegative) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              GetStatus(_, _, _, _, _))
+      .WillOnce(DoAll(SetArgPointee<4>(static_cast<int64_t>(-1024)),
+                      Return(true)));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_payload_size());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetCurrChannelOkay) {
+  const string kChannelName("foo-channel");
+  OmahaRequestParams request_params(&fake_sys_state_);
+  request_params.Init("", "", false);
+  request_params.set_current_channel(kChannelName);
+  fake_sys_state_.set_request_params(&request_params);
+  UmTestUtils::ExpectVariableHasValue(kChannelName,
+                                      provider_->var_curr_channel());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetCurrChannelFailEmpty) {
+  OmahaRequestParams request_params(&fake_sys_state_);
+  request_params.Init("", "", false);
+  request_params.set_current_channel("");
+  fake_sys_state_.set_request_params(&request_params);
+  UmTestUtils::ExpectVariableNotSet(provider_->var_curr_channel());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetNewChannelOkay) {
+  const string kChannelName("foo-channel");
+  OmahaRequestParams request_params(&fake_sys_state_);
+  request_params.Init("", "", false);
+  request_params.set_target_channel(kChannelName);
+  fake_sys_state_.set_request_params(&request_params);
+  UmTestUtils::ExpectVariableHasValue(kChannelName,
+                                      provider_->var_new_channel());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetNewChannelFailEmpty) {
+  OmahaRequestParams request_params(&fake_sys_state_);
+  request_params.Init("", "", false);
+  request_params.set_target_channel("");
+  fake_sys_state_.set_request_params(&request_params);
+  UmTestUtils::ExpectVariableNotSet(provider_->var_new_channel());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetP2PEnabledOkayPrefDoesntExist) {
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_p2p_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetP2PEnabledOkayPrefReadsFalse) {
+  fake_prefs_.SetBoolean(chromeos_update_engine::kPrefsP2PEnabled, false);
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_p2p_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetP2PEnabledReadWhenInitialized) {
+  fake_prefs_.SetBoolean(chromeos_update_engine::kPrefsP2PEnabled, true);
+  SetUp();
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_p2p_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetP2PEnabledUpdated) {
+  fake_prefs_.SetBoolean(chromeos_update_engine::kPrefsP2PEnabled, false);
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_p2p_enabled());
+  fake_prefs_.SetBoolean(chromeos_update_engine::kPrefsP2PEnabled, true);
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_p2p_enabled());
+  fake_prefs_.Delete(chromeos_update_engine::kPrefsP2PEnabled);
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_p2p_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetCellularEnabledOkayPrefDoesntExist) {
+  UmTestUtils::ExpectVariableHasValue(false, provider_->var_cellular_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetCellularEnabledOkayPrefReadsTrue) {
+  fake_prefs_.SetBoolean(
+      chromeos_update_engine::kPrefsUpdateOverCellularPermission, true);
+  UmTestUtils::ExpectVariableHasValue(true, provider_->var_cellular_enabled());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetUpdateCompletedTimeOkay) {
+  Time expected = SetupUpdateCompletedTime(true);
+  UmTestUtils::ExpectVariableHasValue(expected,
+                                      provider_->var_update_completed_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetUpdateCompletedTimeFailNoValue) {
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(), GetBootTimeAtUpdate(_))
+      .WillOnce(Return(false));
+  UmTestUtils::ExpectVariableNotSet(provider_->var_update_completed_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetUpdateCompletedTimeFailInvalidValue) {
+  SetupUpdateCompletedTime(false);
+  UmTestUtils::ExpectVariableNotSet(provider_->var_update_completed_time());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetConsecutiveFailedUpdateChecks) {
+  const unsigned int kNumFailedChecks = 3;
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              consecutive_failed_update_checks())
+      .WillRepeatedly(Return(kNumFailedChecks));
+  UmTestUtils::ExpectVariableHasValue(
+      kNumFailedChecks, provider_->var_consecutive_failed_update_checks());
+}
+
+TEST_F(UmRealUpdaterProviderTest, GetServerDictatedPollInterval) {
+  const unsigned int kPollInterval = 2 * 60 * 60;  // Two hours.
+  EXPECT_CALL(*fake_sys_state_.mock_update_attempter(),
+              server_dictated_poll_interval())
+      .WillRepeatedly(Return(kPollInterval));
+  UmTestUtils::ExpectVariableHasValue(
+      kPollInterval, provider_->var_server_dictated_poll_interval());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/shill_provider.h b/update_manager/shill_provider.h
new file mode 100644
index 0000000..b40f255
--- /dev/null
+++ b/update_manager/shill_provider.h
@@ -0,0 +1,72 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_SHILL_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_SHILL_PROVIDER_H_
+
+#include <base/time/time.h>
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+enum class ConnectionType {
+  kEthernet,
+  kWifi,
+  kWimax,
+  kBluetooth,
+  kCellular,
+  kUnknown
+};
+
+enum class ConnectionTethering {
+  kNotDetected,
+  kSuspected,
+  kConfirmed,
+  kUnknown,
+};
+
+// Provider for networking related information.
+class ShillProvider : public Provider {
+ public:
+  ~ShillProvider() override {}
+
+  // A variable returning whether we currently have network connectivity.
+  virtual Variable<bool>* var_is_connected() = 0;
+
+  // A variable returning the current network connection type. Unknown if not
+  // connected.
+  virtual Variable<ConnectionType>* var_conn_type() = 0;
+
+  // A variable returning the tethering mode of a network connection. Unknown if
+  // not connected.
+  virtual Variable<ConnectionTethering>* var_conn_tethering() = 0;
+
+  // A variable returning the time when network connection last changed.
+  // Initialized to current time.
+  virtual Variable<base::Time>* var_conn_last_changed() = 0;
+
+ protected:
+  ShillProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ShillProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_SHILL_PROVIDER_H_
diff --git a/update_manager/state.h b/update_manager/state.h
new file mode 100644
index 0000000..d428059
--- /dev/null
+++ b/update_manager/state.h
@@ -0,0 +1,54 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_STATE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_STATE_H_
+
+#include "update_engine/update_manager/config_provider.h"
+#include "update_engine/update_manager/device_policy_provider.h"
+#include "update_engine/update_manager/random_provider.h"
+#include "update_engine/update_manager/shill_provider.h"
+#include "update_engine/update_manager/system_provider.h"
+#include "update_engine/update_manager/time_provider.h"
+#include "update_engine/update_manager/updater_provider.h"
+
+namespace chromeos_update_manager {
+
+// The State class is an interface to the ensemble of providers. This class
+// gives visibility of the state providers to policy implementations.
+class State {
+ public:
+  virtual ~State() {}
+
+  // These methods return the given provider.
+  virtual ConfigProvider* config_provider() = 0;
+  virtual DevicePolicyProvider* device_policy_provider() = 0;
+  virtual RandomProvider* random_provider() = 0;
+  virtual ShillProvider* shill_provider() = 0;
+  virtual SystemProvider* system_provider() = 0;
+  virtual TimeProvider* time_provider() = 0;
+  virtual UpdaterProvider* updater_provider() = 0;
+
+ protected:
+  State() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(State);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_STATE_H_
diff --git a/update_manager/state_factory.cc b/update_manager/state_factory.cc
new file mode 100644
index 0000000..d4f4aa4
--- /dev/null
+++ b/update_manager/state_factory.cc
@@ -0,0 +1,77 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/state_factory.h"
+
+#include <memory>
+
+#include <base/logging.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/update_manager/real_config_provider.h"
+#include "update_engine/update_manager/real_device_policy_provider.h"
+#include "update_engine/update_manager/real_random_provider.h"
+#include "update_engine/update_manager/real_shill_provider.h"
+#include "update_engine/update_manager/real_state.h"
+#include "update_engine/update_manager/real_system_provider.h"
+#include "update_engine/update_manager/real_time_provider.h"
+#include "update_engine/update_manager/real_updater_provider.h"
+
+using std::unique_ptr;
+
+namespace chromeos_update_manager {
+
+State* DefaultStateFactory(
+    policy::PolicyProvider* policy_provider,
+    chromeos_update_engine::ShillProxy* shill_proxy,
+    org::chromium::SessionManagerInterfaceProxyInterface* session_manager_proxy,
+    chromeos_update_engine::SystemState* system_state) {
+  chromeos_update_engine::ClockInterface* const clock = system_state->clock();
+  unique_ptr<RealConfigProvider> config_provider(
+      new RealConfigProvider(system_state->hardware()));
+  unique_ptr<RealDevicePolicyProvider> device_policy_provider(
+      new RealDevicePolicyProvider(session_manager_proxy, policy_provider));
+  unique_ptr<RealRandomProvider> random_provider(new RealRandomProvider());
+  unique_ptr<RealShillProvider> shill_provider(
+      new RealShillProvider(shill_proxy, clock));
+  unique_ptr<RealSystemProvider> system_provider(
+      new RealSystemProvider(system_state->hardware(),
+                             system_state->boot_control()));
+  unique_ptr<RealTimeProvider> time_provider(new RealTimeProvider(clock));
+  unique_ptr<RealUpdaterProvider> updater_provider(
+      new RealUpdaterProvider(system_state));
+
+  if (!(config_provider->Init() &&
+        device_policy_provider->Init() &&
+        random_provider->Init() &&
+        shill_provider->Init() &&
+        system_provider->Init() &&
+        time_provider->Init() &&
+        updater_provider->Init())) {
+    LOG(ERROR) << "Error initializing providers";
+    return nullptr;
+  }
+
+  return new RealState(config_provider.release(),
+                       device_policy_provider.release(),
+                       random_provider.release(),
+                       shill_provider.release(),
+                       system_provider.release(),
+                       time_provider.release(),
+                       updater_provider.release());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/state_factory.h b/update_manager/state_factory.h
new file mode 100644
index 0000000..f15fd83
--- /dev/null
+++ b/update_manager/state_factory.h
@@ -0,0 +1,41 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_STATE_FACTORY_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_STATE_FACTORY_H_
+
+#include <session_manager/dbus-proxies.h>
+
+#include "update_engine/shill_proxy.h"
+#include "update_engine/system_state.h"
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+// Creates and initializes a new UpdateManager State instance containing real
+// providers instantiated using the passed interfaces. The State doesn't take
+// ownership of the passed interfaces, which need to remain available during the
+// life of this instance.  Returns null if one of the underlying providers fails
+// to initialize.
+State* DefaultStateFactory(
+    policy::PolicyProvider* policy_provider,
+    chromeos_update_engine::ShillProxy* shill_proxy,
+    org::chromium::SessionManagerInterfaceProxyInterface* session_manager_proxy,
+    chromeos_update_engine::SystemState* system_state);
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_STATE_FACTORY_H_
diff --git a/update_manager/system_provider.h b/update_manager/system_provider.h
new file mode 100644
index 0000000..00fb9af
--- /dev/null
+++ b/update_manager/system_provider.h
@@ -0,0 +1,54 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_SYSTEM_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_SYSTEM_PROVIDER_H_
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Provider for system information, mostly constant, such as the information
+// reported by crossystem, the kernel boot command line and the partition table.
+class SystemProvider : public Provider {
+ public:
+  ~SystemProvider() override {}
+
+  // Returns true if the boot mode is normal or if it's unable to
+  // determine the boot mode. Returns false if the boot mode is
+  // developer.
+  virtual Variable<bool>* var_is_normal_boot_mode() = 0;
+
+  // Returns whether this is an official Chrome OS build.
+  virtual Variable<bool>* var_is_official_build() = 0;
+
+  // Returns a variable that tells whether OOBE was completed.
+  virtual Variable<bool>* var_is_oobe_complete() = 0;
+
+  // Returns a variable that tells the number of slots in the system.
+  virtual Variable<unsigned int>* var_num_slots() = 0;
+
+ protected:
+  SystemProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(SystemProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_SYSTEM_PROVIDER_H_
diff --git a/update_manager/time_provider.h b/update_manager/time_provider.h
new file mode 100644
index 0000000..663ec2c
--- /dev/null
+++ b/update_manager/time_provider.h
@@ -0,0 +1,48 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_TIME_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_TIME_PROVIDER_H_
+
+#include <base/time/time.h>
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// Provider for time related information.
+class TimeProvider : public Provider {
+ public:
+  ~TimeProvider() override {}
+
+  // Returns the current date. The time of day component will be zero.
+  virtual Variable<base::Time>* var_curr_date() = 0;
+
+  // Returns the current hour (0 to 23) in local time. The type is int to keep
+  // consistent with base::Time.
+  virtual Variable<int>* var_curr_hour() = 0;
+
+ protected:
+  TimeProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(TimeProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_TIME_PROVIDER_H_
diff --git a/update_manager/umtest_utils.cc b/update_manager/umtest_utils.cc
new file mode 100644
index 0000000..aa88141
--- /dev/null
+++ b/update_manager/umtest_utils.cc
@@ -0,0 +1,29 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/umtest_utils.h"
+
+#include <base/time/time.h>
+
+namespace chromeos_update_manager {
+
+const unsigned UmTestUtils::kDefaultTimeoutInSeconds = 1;
+
+void PrintTo(const EvalStatus& status, ::std::ostream* os) {
+  *os << ToString(status);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/umtest_utils.h b/update_manager/umtest_utils.h
new file mode 100644
index 0000000..80693db
--- /dev/null
+++ b/update_manager/umtest_utils.h
@@ -0,0 +1,68 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_UMTEST_UTILS_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_UMTEST_UTILS_H_
+
+#include <iostream>  // NOLINT(readability/streams)
+#include <memory>
+
+#include <base/time/time.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+// A help class with common functionality for use in Update Manager testing.
+class UmTestUtils {
+ public:
+  // A default timeout to use when making various queries.
+  static const base::TimeDelta DefaultTimeout() {
+    return base::TimeDelta::FromSeconds(kDefaultTimeoutInSeconds);
+  }
+
+  // Calls GetValue on |variable| and expects its result to be |expected|.
+  template<typename T>
+  static void ExpectVariableHasValue(const T& expected, Variable<T>* variable) {
+    ASSERT_NE(nullptr, variable);
+    std::unique_ptr<const T> value(
+        variable->GetValue(DefaultTimeout(), nullptr));
+    ASSERT_NE(nullptr, value.get()) << "Variable: " << variable->GetName();
+    EXPECT_EQ(expected, *value) << "Variable: " << variable->GetName();
+  }
+
+  // Calls GetValue on |variable| and expects its result to be null.
+  template<typename T>
+  static void ExpectVariableNotSet(Variable<T>* variable) {
+    ASSERT_NE(nullptr, variable);
+    std::unique_ptr<const T> value(
+        variable->GetValue(DefaultTimeout(), nullptr));
+    EXPECT_EQ(nullptr, value.get()) << "Variable: " << variable->GetName();
+  }
+
+ private:
+  static const unsigned kDefaultTimeoutInSeconds;
+};
+
+// PrintTo() functions are used by gtest to print these values. They need to be
+// defined on the same namespace where the type was defined.
+void PrintTo(const EvalStatus& status, ::std::ostream* os);
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_UMTEST_UTILS_H_
diff --git a/update_manager/update_manager-inl.h b/update_manager/update_manager-inl.h
new file mode 100644
index 0000000..77224cf
--- /dev/null
+++ b/update_manager/update_manager-inl.h
@@ -0,0 +1,165 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_INL_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_INL_H_
+
+#include <memory>
+#include <string>
+
+#include <base/bind.h>
+#include <base/location.h>
+#include <brillo/message_loops/message_loop.h>
+
+#include "update_engine/update_manager/evaluation_context.h"
+
+namespace chromeos_update_manager {
+
+template<typename R, typename... Args>
+EvalStatus UpdateManager::EvaluatePolicy(
+    EvaluationContext* ec,
+    EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                        std::string*, R*,
+                                        Args...) const,
+    R* result, Args... args) {
+  // If expiration timeout fired, dump the context and reset expiration.
+  // IMPORTANT: We must still proceed with evaluation of the policy in this
+  // case, so that the evaluation time (and corresponding reevaluation timeouts)
+  // are readjusted.
+  if (ec->is_expired()) {
+    LOG(WARNING) << "Request timed out, evaluation context: "
+                 << ec->DumpContext();
+    ec->ResetExpiration();
+  }
+
+  // Reset the evaluation context.
+  ec->ResetEvaluation();
+
+  const std::string policy_name = policy_->PolicyRequestName(policy_method);
+  LOG(INFO) << policy_name << ": START";
+
+  // First try calling the actual policy.
+  std::string error;
+  EvalStatus status = (policy_.get()->*policy_method)(ec, state_.get(), &error,
+                                                      result, args...);
+  // If evaluating the main policy failed, defer to the default policy.
+  if (status == EvalStatus::kFailed) {
+    LOG(WARNING) << "Evaluating policy failed: " << error
+                 << "\nEvaluation context: " << ec->DumpContext();
+    error.clear();
+    status = (default_policy_.*policy_method)(ec, state_.get(), &error, result,
+                                              args...);
+    if (status == EvalStatus::kFailed) {
+      LOG(WARNING) << "Evaluating default policy failed: " << error;
+    } else if (status == EvalStatus::kAskMeAgainLater) {
+      LOG(ERROR)
+          << "Default policy would block; this is a bug, forcing failure.";
+      status = EvalStatus::kFailed;
+    }
+  }
+
+  LOG(INFO) << policy_name << ": END";
+
+  return status;
+}
+
+template<typename R, typename... Args>
+void UpdateManager::OnPolicyReadyToEvaluate(
+    scoped_refptr<EvaluationContext> ec,
+    base::Callback<void(EvalStatus status, const R& result)> callback,
+    EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                        std::string*, R*,
+                                        Args...) const,
+    Args... args) {
+  // Evaluate the policy.
+  R result;
+  EvalStatus status = EvaluatePolicy(ec.get(), policy_method, &result, args...);
+
+  if (status != EvalStatus::kAskMeAgainLater) {
+    // AsyncPolicyRequest finished.
+    callback.Run(status, result);
+    return;
+  }
+
+  // Re-schedule the policy request based on used variables.
+  base::Closure reeval_callback = base::Bind(
+      &UpdateManager::OnPolicyReadyToEvaluate<R, Args...>,
+      base::Unretained(this), ec, callback,
+      policy_method, args...);
+  if (ec->RunOnValueChangeOrTimeout(reeval_callback))
+    return;  // Reevaluation scheduled successfully.
+
+  // Scheduling a reevaluation can fail because policy method didn't use any
+  // non-const variable nor there's any time-based event that will change the
+  // status of evaluation.  Alternatively, this may indicate an error in the use
+  // of the scheduling interface.
+  LOG(ERROR) << "Failed to schedule a reevaluation of policy "
+             << policy_->PolicyRequestName(policy_method) << "; this is a bug.";
+  callback.Run(status, result);
+}
+
+template<typename R, typename... ActualArgs, typename... ExpectedArgs>
+EvalStatus UpdateManager::PolicyRequest(
+    EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                        std::string*, R*,
+                                        ExpectedArgs...) const,
+    R* result, ActualArgs... args) {
+  scoped_refptr<EvaluationContext> ec(
+      new EvaluationContext(clock_, evaluation_timeout_));
+  // A PolicyRequest always consists on a single evaluation on a new
+  // EvaluationContext.
+  // IMPORTANT: To ensure that ActualArgs can be converted to ExpectedArgs, we
+  // explicitly instantiate EvaluatePolicy with the latter in lieu of the
+  // former.
+  EvalStatus ret = EvaluatePolicy<R, ExpectedArgs...>(ec.get(), policy_method,
+                                                      result, args...);
+  // Sync policy requests must not block, if they do then this is an error.
+  DCHECK(EvalStatus::kAskMeAgainLater != ret);
+  LOG_IF(WARNING, EvalStatus::kAskMeAgainLater == ret)
+      << "Sync request used with an async policy; this is a bug";
+  return ret;
+}
+
+template<typename R, typename... ActualArgs, typename... ExpectedArgs>
+void UpdateManager::AsyncPolicyRequest(
+    base::Callback<void(EvalStatus, const R& result)> callback,
+    EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                        std::string*, R*,
+                                        ExpectedArgs...) const,
+    ActualArgs... args) {
+  scoped_refptr<EvaluationContext> ec =
+      new EvaluationContext(
+          clock_, evaluation_timeout_, expiration_timeout_,
+          std::unique_ptr<base::Callback<void(EvaluationContext*)>>(
+              new base::Callback<void(EvaluationContext*)>(
+                  base::Bind(&UpdateManager::UnregisterEvalContext,
+                             weak_ptr_factory_.GetWeakPtr()))));
+  if (!ec_repo_.insert(ec.get()).second) {
+    LOG(ERROR) << "Failed to register evaluation context; this is a bug.";
+  }
+
+  // IMPORTANT: To ensure that ActualArgs can be converted to ExpectedArgs, we
+  // explicitly instantiate UpdateManager::OnPolicyReadyToEvaluate with the
+  // latter in lieu of the former.
+  base::Closure eval_callback = base::Bind(
+      &UpdateManager::OnPolicyReadyToEvaluate<R, ExpectedArgs...>,
+      base::Unretained(this), ec, callback, policy_method, args...);
+  brillo::MessageLoop::current()->PostTask(FROM_HERE, eval_callback);
+}
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_INL_H_
diff --git a/update_manager/update_manager.cc b/update_manager/update_manager.cc
new file mode 100644
index 0000000..8e9b221
--- /dev/null
+++ b/update_manager/update_manager.cc
@@ -0,0 +1,50 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/update_manager.h"
+
+#include "update_engine/update_manager/chromeos_policy.h"
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+UpdateManager::UpdateManager(chromeos_update_engine::ClockInterface* clock,
+                             base::TimeDelta evaluation_timeout,
+                             base::TimeDelta expiration_timeout, State* state)
+      : default_policy_(clock), state_(state), clock_(clock),
+        evaluation_timeout_(evaluation_timeout),
+        expiration_timeout_(expiration_timeout),
+        weak_ptr_factory_(this) {
+  // TODO(deymo): Make it possible to replace this policy with a different
+  // implementation with a build-time flag.
+  policy_.reset(new ChromeOSPolicy());
+}
+
+UpdateManager::~UpdateManager() {
+  // Remove pending main loop events associated with any of the outstanding
+  // evaluation contexts. This will prevent dangling pending events, causing
+  // these contexts to be destructed once the repo itself is destructed.
+  for (auto& ec : ec_repo_)
+    ec->RemoveObserversAndTimeout();
+}
+
+void UpdateManager::UnregisterEvalContext(EvaluationContext* ec) {
+  if (!ec_repo_.erase(ec)) {
+    LOG(ERROR) << "Unregistering an unknown evaluation context, this is a bug.";
+  }
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/update_manager.conf.example b/update_manager/update_manager.conf.example
new file mode 100644
index 0000000..2d77974
--- /dev/null
+++ b/update_manager/update_manager.conf.example
@@ -0,0 +1,18 @@
+# Configuration file for the update-manager component of update_engine.
+#
+# Normally this file is loaded from /etc/update_manager.conf. If
+# running update_engine in developer mode (and only if running in
+# developer mode), we attempt to load
+#
+#  /mnt/stateful_partition/etc/update_manager.conf
+#
+# and use it if it exists. If it doesn't exist, we fall back to
+# /etc/update_manager.conf.
+#
+# Note: changes to this file are not automatically applied. Use the
+# command "restart update-engine" from a root shell to make your
+# changes take effect.
+
+# Set to true if the device supports the concept of OOBE
+# (Out-Of-the-Box-Experience), false if it doesn't.
+is_oobe_enabled=true
diff --git a/update_manager/update_manager.h b/update_manager/update_manager.h
new file mode 100644
index 0000000..a2f35df
--- /dev/null
+++ b/update_manager/update_manager.h
@@ -0,0 +1,178 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_H_
+
+#include <memory>
+#include <set>
+#include <string>
+
+#include <base/callback.h>
+#include <base/memory/ref_counted.h>
+#include <base/time/time.h>
+
+#include "update_engine/common/clock_interface.h"
+#include "update_engine/update_manager/default_policy.h"
+#include "update_engine/update_manager/evaluation_context.h"
+#include "update_engine/update_manager/policy.h"
+#include "update_engine/update_manager/state.h"
+
+namespace chromeos_update_manager {
+
+// Comparator for scoped_refptr objects.
+template<typename T>
+struct ScopedRefPtrLess {
+  bool operator()(const scoped_refptr<T>& first,
+                  const scoped_refptr<T>& second) const {
+    return first.get() < second.get();
+  }
+};
+
+// The main Update Manager singleton class.
+class UpdateManager {
+ public:
+  // Creates the UpdateManager instance, assuming ownership on the provided
+  // |state|.
+  UpdateManager(chromeos_update_engine::ClockInterface* clock,
+                base::TimeDelta evaluation_timeout,
+                base::TimeDelta expiration_timeout, State* state);
+
+  virtual ~UpdateManager();
+
+  // PolicyRequest() evaluates the given policy with the provided arguments and
+  // returns the result. The |policy_method| is the pointer-to-method of the
+  // Policy class for the policy request to call. The UpdateManager will call
+  // this method on the right policy. The pointer |result| must not be null
+  // and the remaining |args| depend on the arguments required by the passed
+  // |policy_method|.
+  //
+  // When the policy request succeeds, the |result| is set and the method
+  // returns EvalStatus::kSucceeded, otherwise, the |result| may not be set.  A
+  // policy called with this method should not block (i.e. return
+  // EvalStatus::kAskMeAgainLater), which is considered a programming error. On
+  // failure, EvalStatus::kFailed is returned.
+  //
+  // An example call to this method is:
+  //   um.PolicyRequest(&Policy::SomePolicyMethod, &bool_result, arg1, arg2);
+  template<typename R, typename... ActualArgs, typename... ExpectedArgs>
+  EvalStatus PolicyRequest(
+      EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                          std::string*, R*,
+                                          ExpectedArgs...) const,
+      R* result, ActualArgs...);
+
+  // Evaluates the given |policy_method| policy with the provided |args|
+  // arguments and calls the |callback| callback with the result when done.
+  //
+  // If the policy implementation should block, returning a
+  // EvalStatus::kAskMeAgainLater status the Update Manager will re-evaluate the
+  // policy until another status is returned. If the policy implementation based
+  // its return value solely on const variables, the callback will be called
+  // with the EvalStatus::kAskMeAgainLater status (which indicates an error).
+  template<typename R, typename... ActualArgs, typename... ExpectedArgs>
+  void AsyncPolicyRequest(
+      base::Callback<void(EvalStatus, const R& result)> callback,
+      EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                          std::string*, R*,
+                                          ExpectedArgs...) const,
+      ActualArgs... args);
+
+ protected:
+  // The UpdateManager receives ownership of the passed Policy instance.
+  void set_policy(const Policy* policy) {
+    policy_.reset(policy);
+  }
+
+  // State getter used for testing.
+  State* state() { return state_.get(); }
+
+ private:
+  FRIEND_TEST(UmUpdateManagerTest, PolicyRequestCallsPolicy);
+  FRIEND_TEST(UmUpdateManagerTest, PolicyRequestCallsDefaultOnError);
+  FRIEND_TEST(UmUpdateManagerTest, PolicyRequestDoesntBlockDeathTest);
+  FRIEND_TEST(UmUpdateManagerTest, AsyncPolicyRequestDelaysEvaluation);
+  FRIEND_TEST(UmUpdateManagerTest, AsyncPolicyRequestTimeoutDoesNotFire);
+  FRIEND_TEST(UmUpdateManagerTest, AsyncPolicyRequestTimesOut);
+
+  // EvaluatePolicy() evaluates the passed |policy_method| method on the current
+  // policy with the given |args| arguments. If the method fails, the default
+  // policy is used instead.
+  template<typename R, typename... Args>
+  EvalStatus EvaluatePolicy(
+      EvaluationContext* ec,
+      EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                          std::string*, R*,
+                                          Args...) const,
+      R* result, Args... args);
+
+  // OnPolicyReadyToEvaluate() is called by the main loop when the evaluation
+  // of the given |policy_method| should be executed. If the evaluation finishes
+  // the |callback| callback is called passing the |result| and the |status|
+  // returned by the policy. If the evaluation returns an
+  // EvalStatus::kAskMeAgainLater state, the |callback| will NOT be called and
+  // the evaluation will be re-scheduled to be called later.
+  template<typename R, typename... Args>
+  void OnPolicyReadyToEvaluate(
+      scoped_refptr<EvaluationContext> ec,
+      base::Callback<void(EvalStatus status, const R& result)> callback,
+      EvalStatus (Policy::*policy_method)(EvaluationContext*, State*,
+                                          std::string*, R*,
+                                          Args...) const,
+      Args... args);
+
+  // Unregisters (removes from repo) a previously created EvaluationContext.
+  void UnregisterEvalContext(EvaluationContext* ec);
+
+  // The policy used by the UpdateManager. Note that since it is a const Policy,
+  // policy implementations are not allowed to persist state on this class.
+  std::unique_ptr<const Policy> policy_;
+
+  // A safe default value to the current policy. This policy is used whenever
+  // a policy implementation fails with EvalStatus::kFailed.
+  const DefaultPolicy default_policy_;
+
+  // State Providers.
+  std::unique_ptr<State> state_;
+
+  // Pointer to the mockable clock interface;
+  chromeos_update_engine::ClockInterface* clock_;
+
+  // Timeout for a policy evaluation.
+  const base::TimeDelta evaluation_timeout_;
+
+  // Timeout for expiration of the evaluation context, used for async requests.
+  const base::TimeDelta expiration_timeout_;
+
+  // Repository of previously created EvaluationContext objects. These are being
+  // unregistered (and the reference released) when the context is being
+  // destructed; alternatively, when the UpdateManager instance is destroyed, it
+  // will remove all pending events associated with all outstanding contexts
+  // (which should, in turn, trigger their destruction).
+  std::set<scoped_refptr<EvaluationContext>,
+           ScopedRefPtrLess<EvaluationContext>> ec_repo_;
+
+  base::WeakPtrFactory<UpdateManager> weak_ptr_factory_;
+
+  DISALLOW_COPY_AND_ASSIGN(UpdateManager);
+};
+
+}  // namespace chromeos_update_manager
+
+// Include the implementation of the template methods.
+#include "update_engine/update_manager/update_manager-inl.h"
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_UPDATE_MANAGER_H_
diff --git a/update_manager/update_manager_unittest.cc b/update_manager/update_manager_unittest.cc
new file mode 100644
index 0000000..4cc738d
--- /dev/null
+++ b/update_manager/update_manager_unittest.cc
@@ -0,0 +1,325 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/update_manager.h"
+
+#include <unistd.h>
+
+#include <algorithm>
+#include <memory>
+#include <string>
+#include <tuple>
+#include <utility>
+#include <vector>
+
+#include <base/bind.h>
+#include <base/test/simple_test_clock.h>
+#include <base/time/time.h>
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+
+#include "update_engine/common/fake_clock.h"
+#include "update_engine/update_manager/default_policy.h"
+#include "update_engine/update_manager/fake_state.h"
+#include "update_engine/update_manager/mock_policy.h"
+#include "update_engine/update_manager/umtest_utils.h"
+
+using base::Bind;
+using base::Callback;
+using base::Time;
+using base::TimeDelta;
+using brillo::MessageLoop;
+using brillo::MessageLoopRunMaxIterations;
+using chromeos_update_engine::ErrorCode;
+using chromeos_update_engine::FakeClock;
+using std::pair;
+using std::string;
+using std::tuple;
+using std::unique_ptr;
+using std::vector;
+
+namespace {
+
+// Generates a fixed timestamp for use in faking the current time.
+Time FixedTime() {
+  Time::Exploded now_exp;
+  now_exp.year = 2014;
+  now_exp.month = 3;
+  now_exp.day_of_week = 2;
+  now_exp.day_of_month = 18;
+  now_exp.hour = 8;
+  now_exp.minute = 5;
+  now_exp.second = 33;
+  now_exp.millisecond = 675;
+  return Time::FromLocalExploded(now_exp);
+}
+
+}  // namespace
+
+namespace chromeos_update_manager {
+
+class UmUpdateManagerTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+    fake_state_ = new FakeState();
+    umut_.reset(new UpdateManager(&fake_clock_, TimeDelta::FromSeconds(5),
+                                  TimeDelta::FromSeconds(1), fake_state_));
+  }
+
+  void TearDown() override {
+    EXPECT_FALSE(loop_.PendingTasks());
+  }
+
+  base::SimpleTestClock test_clock_;
+  brillo::FakeMessageLoop loop_{&test_clock_};
+  FakeState* fake_state_;  // Owned by the umut_.
+  FakeClock fake_clock_;
+  unique_ptr<UpdateManager> umut_;
+};
+
+// The FailingPolicy implements a single method and make it always fail. This
+// class extends the DefaultPolicy class to allow extensions of the Policy
+// class without extending nor changing this test.
+class FailingPolicy : public DefaultPolicy {
+ public:
+  explicit FailingPolicy(int* num_called_p) : num_called_p_(num_called_p) {}
+  FailingPolicy() : FailingPolicy(nullptr) {}
+  EvalStatus UpdateCheckAllowed(EvaluationContext* ec, State* state,
+                                string* error,
+                                UpdateCheckParams* result) const override {
+    if (num_called_p_)
+      (*num_called_p_)++;
+    *error = "FailingPolicy failed.";
+    return EvalStatus::kFailed;
+  }
+
+ protected:
+  string PolicyName() const override { return "FailingPolicy"; }
+
+ private:
+  int* num_called_p_;
+};
+
+// The LazyPolicy always returns EvalStatus::kAskMeAgainLater.
+class LazyPolicy : public DefaultPolicy {
+  EvalStatus UpdateCheckAllowed(EvaluationContext* ec, State* state,
+                                string* error,
+                                UpdateCheckParams* result) const override {
+    return EvalStatus::kAskMeAgainLater;
+  }
+
+ protected:
+  string PolicyName() const override { return "LazyPolicy"; }
+};
+
+// A policy that sleeps for a predetermined amount of time, then checks for a
+// wallclock-based time threshold (if given) and returns
+// EvalStatus::kAskMeAgainLater if not passed; otherwise, returns
+// EvalStatus::kSucceeded. Increments a counter every time it is being queried,
+// if a pointer to it is provided.
+class DelayPolicy : public DefaultPolicy {
+ public:
+  DelayPolicy(int sleep_secs, Time time_threshold, int* num_called_p)
+      : sleep_secs_(sleep_secs), time_threshold_(time_threshold),
+        num_called_p_(num_called_p) {}
+  EvalStatus UpdateCheckAllowed(EvaluationContext* ec, State* state,
+                                string* error,
+                                UpdateCheckParams* result) const override {
+    if (num_called_p_)
+      (*num_called_p_)++;
+
+    // Sleep for a predetermined amount of time.
+    if (sleep_secs_ > 0)
+      sleep(sleep_secs_);
+
+    // Check for a time threshold. This can be used to ensure that the policy
+    // has some non-constant dependency.
+    if (time_threshold_ < Time::Max() &&
+        ec->IsWallclockTimeGreaterThan(time_threshold_))
+      return EvalStatus::kSucceeded;
+
+    return EvalStatus::kAskMeAgainLater;
+  }
+
+ protected:
+  string PolicyName() const override { return "DelayPolicy"; }
+
+ private:
+  int sleep_secs_;
+  Time time_threshold_;
+  int* num_called_p_;
+};
+
+// AccumulateCallsCallback() adds to the passed |acc| accumulator vector pairs
+// of EvalStatus and T instances. This allows to create a callback that keeps
+// track of when it is called and the arguments passed to it, to be used with
+// the UpdateManager::AsyncPolicyRequest().
+template<typename T>
+static void AccumulateCallsCallback(vector<pair<EvalStatus, T>>* acc,
+                                    EvalStatus status, const T& result) {
+  acc->push_back(std::make_pair(status, result));
+}
+
+// Tests that policy requests are completed successfully. It is important that
+// this tests cover all policy requests as defined in Policy.
+TEST_F(UmUpdateManagerTest, PolicyRequestCallUpdateCheckAllowed) {
+  UpdateCheckParams result;
+  EXPECT_EQ(EvalStatus::kSucceeded, umut_->PolicyRequest(
+      &Policy::UpdateCheckAllowed, &result));
+}
+
+TEST_F(UmUpdateManagerTest, PolicyRequestCallUpdateCanStart) {
+  UpdateState update_state = UpdateState();
+  update_state.is_interactive = true;
+  update_state.is_delta_payload = false;
+  update_state.first_seen = FixedTime();
+  update_state.num_checks = 1;
+  update_state.num_failures = 0;
+  update_state.failures_last_updated = Time();
+  update_state.download_urls = vector<string>{"http://fake/url/"};
+  update_state.download_errors_max = 10;
+  update_state.p2p_downloading_disabled = false;
+  update_state.p2p_sharing_disabled = false;
+  update_state.p2p_num_attempts = 0;
+  update_state.p2p_first_attempted = Time();
+  update_state.last_download_url_idx = -1;
+  update_state.last_download_url_num_errors = 0;
+  update_state.download_errors = vector<tuple<int, ErrorCode, Time>>();
+  update_state.backoff_expiry = Time();
+  update_state.is_backoff_disabled = false;
+  update_state.scatter_wait_period = TimeDelta::FromSeconds(15);
+  update_state.scatter_check_threshold = 4;
+  update_state.scatter_wait_period_max = TimeDelta::FromSeconds(60);
+  update_state.scatter_check_threshold_min = 2;
+  update_state.scatter_check_threshold_max = 8;
+
+  UpdateDownloadParams result;
+  EXPECT_EQ(EvalStatus::kSucceeded,
+            umut_->PolicyRequest(&Policy::UpdateCanStart, &result,
+                                 update_state));
+}
+
+TEST_F(UmUpdateManagerTest, PolicyRequestCallsDefaultOnError) {
+  umut_->set_policy(new FailingPolicy());
+
+  // Tests that the DefaultPolicy instance is called when the method fails,
+  // which will set this as true.
+  UpdateCheckParams result;
+  result.updates_enabled = false;
+  EvalStatus status = umut_->PolicyRequest(
+      &Policy::UpdateCheckAllowed, &result);
+  EXPECT_EQ(EvalStatus::kSucceeded, status);
+  EXPECT_TRUE(result.updates_enabled);
+}
+
+// This test only applies to debug builds where DCHECK is enabled.
+#if DCHECK_IS_ON
+TEST_F(UmUpdateManagerTest, PolicyRequestDoesntBlockDeathTest) {
+  // The update manager should die (DCHECK) if a policy called synchronously
+  // returns a kAskMeAgainLater value.
+  UpdateCheckParams result;
+  umut_->set_policy(new LazyPolicy());
+  EXPECT_DEATH(umut_->PolicyRequest(&Policy::UpdateCheckAllowed, &result), "");
+}
+#endif  // DCHECK_IS_ON
+
+TEST_F(UmUpdateManagerTest, AsyncPolicyRequestDelaysEvaluation) {
+  // To avoid differences in code execution order between an AsyncPolicyRequest
+  // call on a policy that returns AskMeAgainLater the first time and one that
+  // succeeds the first time, we ensure that the passed callback is called from
+  // the main loop in both cases even when we could evaluate it right now.
+  umut_->set_policy(new FailingPolicy());
+
+  vector<pair<EvalStatus, UpdateCheckParams>> calls;
+  Callback<void(EvalStatus, const UpdateCheckParams&)> callback = Bind(
+      AccumulateCallsCallback<UpdateCheckParams>, &calls);
+
+  umut_->AsyncPolicyRequest(callback, &Policy::UpdateCheckAllowed);
+  // The callback should wait until we run the main loop for it to be executed.
+  EXPECT_EQ(0, calls.size());
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(1, calls.size());
+}
+
+TEST_F(UmUpdateManagerTest, AsyncPolicyRequestTimeoutDoesNotFire) {
+  // Set up an async policy call to return immediately, then wait a little and
+  // ensure that the timeout event does not fire.
+  int num_called = 0;
+  umut_->set_policy(new FailingPolicy(&num_called));
+
+  vector<pair<EvalStatus, UpdateCheckParams>> calls;
+  Callback<void(EvalStatus, const UpdateCheckParams&)> callback =
+      Bind(AccumulateCallsCallback<UpdateCheckParams>, &calls);
+
+  umut_->AsyncPolicyRequest(callback, &Policy::UpdateCheckAllowed);
+  // Run the main loop, ensure that policy was attempted once before deferring
+  // to the default.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(1, num_called);
+  ASSERT_EQ(1, calls.size());
+  EXPECT_EQ(EvalStatus::kSucceeded, calls[0].first);
+  // Wait for the timeout to expire, run the main loop again, ensure that
+  // nothing happened.
+  test_clock_.Advance(TimeDelta::FromSeconds(2));
+  MessageLoopRunMaxIterations(MessageLoop::current(), 10);
+  EXPECT_EQ(1, num_called);
+  EXPECT_EQ(1, calls.size());
+}
+
+TEST_F(UmUpdateManagerTest, AsyncPolicyRequestTimesOut) {
+  // Set up an async policy call to exceed its expiration timeout, make sure
+  // that the default policy was not used (no callback) and that evaluation is
+  // reattempted.
+  int num_called = 0;
+  umut_->set_policy(new DelayPolicy(
+          0, fake_clock_.GetWallclockTime() + TimeDelta::FromSeconds(3),
+          &num_called));
+
+  vector<pair<EvalStatus, UpdateCheckParams>> calls;
+  Callback<void(EvalStatus, const UpdateCheckParams&)> callback =
+      Bind(AccumulateCallsCallback<UpdateCheckParams>, &calls);
+
+  umut_->AsyncPolicyRequest(callback, &Policy::UpdateCheckAllowed);
+  // Run the main loop, ensure that policy was attempted once but the callback
+  // was not invoked.
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+  EXPECT_EQ(1, num_called);
+  EXPECT_EQ(0, calls.size());
+  // Wait for the expiration timeout to expire, run the main loop again,
+  // ensure that reevaluation occurred but callback was not invoked (i.e.
+  // default policy was not consulted).
+  test_clock_.Advance(TimeDelta::FromSeconds(2));
+  fake_clock_.SetWallclockTime(fake_clock_.GetWallclockTime() +
+                               TimeDelta::FromSeconds(2));
+  MessageLoopRunMaxIterations(MessageLoop::current(), 10);
+  EXPECT_EQ(2, num_called);
+  EXPECT_EQ(0, calls.size());
+  // Wait for reevaluation due to delay to happen, ensure that it occurs and
+  // that the callback is invoked.
+  test_clock_.Advance(TimeDelta::FromSeconds(2));
+  fake_clock_.SetWallclockTime(fake_clock_.GetWallclockTime() +
+                               TimeDelta::FromSeconds(2));
+  MessageLoopRunMaxIterations(MessageLoop::current(), 10);
+  EXPECT_EQ(3, num_called);
+  ASSERT_EQ(1, calls.size());
+  EXPECT_EQ(EvalStatus::kSucceeded, calls[0].first);
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_manager/updater_provider.h b/update_manager/updater_provider.h
new file mode 100644
index 0000000..8048d38
--- /dev/null
+++ b/update_manager/updater_provider.h
@@ -0,0 +1,117 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_UPDATER_PROVIDER_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_UPDATER_PROVIDER_H_
+
+#include <string>
+
+#include <base/time/time.h>
+
+#include "update_engine/update_manager/provider.h"
+#include "update_engine/update_manager/variable.h"
+
+namespace chromeos_update_manager {
+
+enum class Stage {
+  kIdle,
+  kCheckingForUpdate,
+  kUpdateAvailable,
+  kDownloading,
+  kVerifying,
+  kFinalizing,
+  kUpdatedNeedReboot,
+  kReportingErrorEvent,
+  kAttemptingRollback,
+};
+
+enum class UpdateRequestStatus {
+  kNone,
+  kInteractive,
+  kPeriodic,
+};
+
+// Provider for Chrome OS update related information.
+class UpdaterProvider : public Provider {
+ public:
+  ~UpdaterProvider() override {}
+
+  // A variable returning the timestamp when the update engine was started in
+  // wallclock time.
+  virtual Variable<base::Time>* var_updater_started_time() = 0;
+
+  // A variable returning the last update check time.
+  virtual Variable<base::Time>* var_last_checked_time() = 0;
+
+  // A variable reporting the time when an update was last completed in the
+  // current boot cycle. Returns an error if an update completed time could not
+  // be read (e.g. no update was completed in the current boot cycle) or is
+  // invalid.
+  //
+  // IMPORTANT: The time reported is not the wallclock time reading at the time
+  // of the update, rather it is the point in time when the update completed
+  // relative to the current wallclock time reading. Therefore, the gap between
+  // the reported value and the current wallclock time is guaranteed to be
+  // monotonically increasing.
+  virtual Variable<base::Time>* var_update_completed_time() = 0;
+
+  // A variable returning the update progress (0.0 to 1.0).
+  virtual Variable<double>* var_progress() = 0;
+
+  // A variable returning the current update status.
+  virtual Variable<Stage>* var_stage() = 0;
+
+  // A variable returning the update target version.
+  virtual Variable<std::string>* var_new_version() = 0;
+
+  // A variable returning the update payload size. The payload size is
+  // guaranteed to be non-negative.
+  virtual Variable<int64_t>* var_payload_size() = 0;
+
+  // A variable returning the current channel.
+  virtual Variable<std::string>* var_curr_channel() = 0;
+
+  // A variable returning the update target channel.
+  virtual Variable<std::string>* var_new_channel() = 0;
+
+  // A variable indicating whether user settings allow P2P updates.
+  virtual Variable<bool>* var_p2p_enabled() = 0;
+
+  // A variable indicating whether user settings allow updates over a cellular
+  // network.
+  virtual Variable<bool>* var_cellular_enabled() = 0;
+
+  // A variable returning the number of consecutive failed update checks.
+  virtual Variable<unsigned int>* var_consecutive_failed_update_checks() = 0;
+
+  // A server-dictated update check interval in seconds, if one was given.
+  virtual Variable<unsigned int>* var_server_dictated_poll_interval() = 0;
+
+  // A variable denoting whether a forced update was request but no update check
+  // performed yet; also tells whether this request is for an interactive or
+  // scheduled update.
+  virtual Variable<UpdateRequestStatus>* var_forced_update_requested() = 0;
+
+ protected:
+  UpdaterProvider() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(UpdaterProvider);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_UPDATER_PROVIDER_H_
diff --git a/update_manager/variable.h b/update_manager/variable.h
new file mode 100644
index 0000000..98774ef
--- /dev/null
+++ b/update_manager/variable.h
@@ -0,0 +1,217 @@
+//
+// Copyright (C) 2014 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_MANAGER_VARIABLE_H_
+#define UPDATE_ENGINE_UPDATE_MANAGER_VARIABLE_H_
+
+#include <algorithm>
+#include <list>
+#include <string>
+
+#include <base/bind.h>
+#include <base/location.h>
+#include <base/logging.h>
+#include <base/time/time.h>
+#include <brillo/message_loops/message_loop.h>
+#include <gtest/gtest_prod.h>  // for FRIEND_TEST
+
+namespace chromeos_update_manager {
+
+// The VariableMode specifies important behavior of the variable in terms of
+// whether, how and when the value of the variable changes.
+enum VariableMode {
+  // Const variables never changes during the life of a policy request, so the
+  // EvaluationContext caches the value even between different evaluations of
+  // the same policy request.
+  kVariableModeConst,
+
+  // Poll variables, or synchronous variables, represent a variable with a value
+  // that can be queried at any time, but it is not known when the value
+  // changes on the source of information. In order to detect if the value of
+  // the variable changes, it has to be queried again.
+  kVariableModePoll,
+
+  // Async variables are able to produce a signal or callback whenever the
+  // value changes. This means that it's not required to poll the value to
+  // detect when it changes, instead, you should register an observer to get
+  // a notification when that happens.
+  kVariableModeAsync,
+};
+
+// This class is a base class with the common functionality that doesn't
+// depend on the variable's type, implemented by all the variables.
+class BaseVariable {
+ public:
+  // Interface for observing changes on variable value.
+  class ObserverInterface {
+   public:
+    virtual ~ObserverInterface() {}
+
+    // Called when the value on the variable changes.
+    virtual void ValueChanged(BaseVariable* variable) = 0;
+  };
+
+  virtual ~BaseVariable() {
+    if (!observer_list_.empty()) {
+      LOG(WARNING) << "Variable " << name_ << " deleted with "
+                   << observer_list_.size() << " observers.";
+    }
+    DCHECK(observer_list_.empty()) << "Don't destroy the variable without "
+                                      "removing the observers.";
+  }
+
+  // Returns the variable name as a string.
+  const std::string& GetName() const {
+    return name_;
+  }
+
+  // Returns the variable mode.
+  VariableMode GetMode() const {
+    return mode_;
+  }
+
+  // For VariableModePoll variables, it returns the polling interval of this
+  // variable. In other case, it returns 0.
+  base::TimeDelta GetPollInterval() const {
+    return poll_interval_;
+  }
+
+  // Adds and removes observers for value changes on the variable. This only
+  // works for kVariableAsync variables since the other modes don't track value
+  // changes. Adding the same observer twice has no effect.
+  virtual void AddObserver(BaseVariable::ObserverInterface* observer) {
+    if (std::find(observer_list_.begin(), observer_list_.end(), observer) ==
+        observer_list_.end()) {
+      observer_list_.push_back(observer);
+    }
+  }
+
+  virtual void RemoveObserver(BaseVariable::ObserverInterface* observer) {
+    observer_list_.remove(observer);
+  }
+
+ protected:
+  // Creates a BaseVariable using the default polling interval (5 minutes).
+  BaseVariable(const std::string& name, VariableMode mode)
+      : BaseVariable(name, mode,
+                     base::TimeDelta::FromMinutes(kDefaultPollMinutes)) {}
+
+  // Creates a BaseVariable with mode kVariableModePoll and the provided
+  // polling interval.
+  BaseVariable(const std::string& name, base::TimeDelta poll_interval)
+      : BaseVariable(name, kVariableModePoll, poll_interval) {}
+
+  // Calls ValueChanged on all the observers.
+  void NotifyValueChanged() {
+    // Fire all the observer methods from the main loop as single call. In order
+    // to avoid scheduling these callbacks when it is not needed, we check
+    // first the list of observers.
+    if (!observer_list_.empty()) {
+      brillo::MessageLoop::current()->PostTask(
+          FROM_HERE,
+          base::Bind(&BaseVariable::OnValueChangedNotification,
+                     base::Unretained(this)));
+    }
+  }
+
+ private:
+  friend class UmEvaluationContextTest;
+  FRIEND_TEST(UmBaseVariableTest, RepeatedObserverTest);
+  FRIEND_TEST(UmBaseVariableTest, NotifyValueChangedTest);
+  FRIEND_TEST(UmBaseVariableTest, NotifyValueRemovesObserversTest);
+
+  BaseVariable(const std::string& name, VariableMode mode,
+               base::TimeDelta poll_interval)
+    : name_(name), mode_(mode),
+      poll_interval_(mode == kVariableModePoll ?
+                     poll_interval : base::TimeDelta()) {}
+
+  void OnValueChangedNotification() {
+    // A ValueChanged() method can change the list of observers, for example
+    // removing itself and invalidating the iterator, so we create a snapshot
+    // of the observers first. Also, to support the case when *another* observer
+    // is removed, we check for them.
+    std::list<BaseVariable::ObserverInterface*> observer_list_copy(
+        observer_list_);
+
+    for (auto& observer : observer_list_copy) {
+      if (std::find(observer_list_.begin(), observer_list_.end(), observer) !=
+          observer_list_.end()) {
+        observer->ValueChanged(this);
+      }
+    }
+  }
+
+  // The default PollInterval in minutes.
+  static constexpr int kDefaultPollMinutes = 5;
+
+  // The variable's name as a string.
+  const std::string name_;
+
+  // The variable's mode.
+  const VariableMode mode_;
+
+  // The variable's polling interval for VariableModePoll variable and 0 for
+  // other modes.
+  const base::TimeDelta poll_interval_;
+
+  // The list of value changes observers.
+  std::list<BaseVariable::ObserverInterface*> observer_list_;
+
+  DISALLOW_COPY_AND_ASSIGN(BaseVariable);
+};
+
+// Interface to an Update Manager variable of a given type. Implementation
+// internals are hidden as protected members, since policies should not be
+// using them directly.
+template<typename T>
+class Variable : public BaseVariable {
+ public:
+  ~Variable() override {}
+
+ protected:
+  // Only allow to get values through the EvaluationContext class and not
+  // directly from the variable.
+  friend class EvaluationContext;
+
+  // Needed to be able to verify variable contents during unit testing.
+  friend class UmTestUtils;
+  FRIEND_TEST(UmRealRandomProviderTest, GetRandomValues);
+
+  Variable(const std::string& name, VariableMode mode)
+      : BaseVariable(name, mode) {}
+
+  Variable(const std::string& name, const base::TimeDelta poll_interval)
+      : BaseVariable(name, poll_interval) {}
+
+  // Gets the current value of the variable. The current value is copied to a
+  // new object and returned. The caller of this method owns the object and
+  // should delete it.
+  //
+  // In case of and error getting the current value or the |timeout| timeout is
+  // exceeded, a null value is returned and the |errmsg| is set.
+  //
+  // The caller can pass a null value for |errmsg|, in which case the error
+  // message won't be set.
+  virtual const T* GetValue(base::TimeDelta timeout, std::string* errmsg) = 0;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(Variable);
+};
+
+}  // namespace chromeos_update_manager
+
+#endif  // UPDATE_ENGINE_UPDATE_MANAGER_VARIABLE_H_
diff --git a/update_manager/variable_unittest.cc b/update_manager/variable_unittest.cc
new file mode 100644
index 0000000..13cceb1
--- /dev/null
+++ b/update_manager/variable_unittest.cc
@@ -0,0 +1,181 @@
+//
+// Copyright (C) 2014 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 "update_engine/update_manager/variable.h"
+
+#include <vector>
+
+#include <brillo/message_loops/fake_message_loop.h>
+#include <brillo/message_loops/message_loop.h>
+#include <brillo/message_loops/message_loop_utils.h>
+#include <gtest/gtest.h>
+
+using base::TimeDelta;
+using brillo::MessageLoop;
+using brillo::MessageLoopRunMaxIterations;
+using std::string;
+using std::vector;
+
+namespace chromeos_update_manager {
+
+// Variable class that returns a value constructed with the default value.
+template <typename T>
+class DefaultVariable : public Variable<T> {
+ public:
+  DefaultVariable(const string& name, VariableMode mode)
+      : Variable<T>(name, mode) {}
+  DefaultVariable(const string& name, const TimeDelta& poll_interval)
+      : Variable<T>(name, poll_interval) {}
+  ~DefaultVariable() override {}
+
+ protected:
+  const T* GetValue(TimeDelta /* timeout */,
+                    string* /* errmsg */) override {
+    return new T();
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(DefaultVariable);
+};
+
+class UmBaseVariableTest : public ::testing::Test {
+ protected:
+  void SetUp() override {
+    loop_.SetAsCurrent();
+  }
+
+  brillo::FakeMessageLoop loop_{nullptr};
+};
+
+TEST_F(UmBaseVariableTest, GetNameTest) {
+  DefaultVariable<int> var("var", kVariableModeConst);
+  EXPECT_EQ(var.GetName(), string("var"));
+}
+
+TEST_F(UmBaseVariableTest, GetModeTest) {
+  DefaultVariable<int> var("var", kVariableModeConst);
+  EXPECT_EQ(var.GetMode(), kVariableModeConst);
+  DefaultVariable<int> other_var("other_var", kVariableModePoll);
+  EXPECT_EQ(other_var.GetMode(), kVariableModePoll);
+}
+
+TEST_F(UmBaseVariableTest, DefaultPollIntervalTest) {
+  DefaultVariable<int> const_var("const_var", kVariableModeConst);
+  EXPECT_EQ(const_var.GetPollInterval(), TimeDelta());
+  DefaultVariable<int> poll_var("poll_var", kVariableModePoll);
+  EXPECT_EQ(poll_var.GetPollInterval(), TimeDelta::FromMinutes(5));
+}
+
+TEST_F(UmBaseVariableTest, GetPollIntervalTest) {
+  DefaultVariable<int> var("var", TimeDelta::FromMinutes(3));
+  EXPECT_EQ(var.GetMode(), kVariableModePoll);
+  EXPECT_EQ(var.GetPollInterval(), TimeDelta::FromMinutes(3));
+}
+
+class BaseVariableObserver : public BaseVariable::ObserverInterface {
+ public:
+  void ValueChanged(BaseVariable* variable) {
+    calls_.push_back(variable);
+  }
+
+  // List of called functions.
+  vector<BaseVariable*> calls_;
+};
+
+TEST_F(UmBaseVariableTest, RepeatedObserverTest) {
+  DefaultVariable<int> var("var", kVariableModeAsync);
+  BaseVariableObserver observer;
+  var.AddObserver(&observer);
+  EXPECT_EQ(var.observer_list_.size(), 1);
+  var.AddObserver(&observer);
+  EXPECT_EQ(var.observer_list_.size(), 1);
+  var.RemoveObserver(&observer);
+  EXPECT_EQ(var.observer_list_.size(), 0);
+  var.RemoveObserver(&observer);
+  EXPECT_EQ(var.observer_list_.size(), 0);
+}
+
+TEST_F(UmBaseVariableTest, NotifyValueChangedTest) {
+  DefaultVariable<int> var("var", kVariableModeAsync);
+  BaseVariableObserver observer1;
+  var.AddObserver(&observer1);
+  // Simulate a value change on the variable's implementation.
+  var.NotifyValueChanged();
+  ASSERT_EQ(0, observer1.calls_.size());
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+
+  ASSERT_EQ(1, observer1.calls_.size());
+  // Check that the observer is called with the right argument.
+  EXPECT_EQ(&var, observer1.calls_[0]);
+
+  BaseVariableObserver observer2;
+  var.AddObserver(&observer2);
+  var.NotifyValueChanged();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+
+  // Check that all the observers are called.
+  EXPECT_EQ(2, observer1.calls_.size());
+  EXPECT_EQ(1, observer2.calls_.size());
+
+  var.RemoveObserver(&observer1);
+  var.RemoveObserver(&observer2);
+}
+
+class BaseVariableObserverRemover : public BaseVariable::ObserverInterface {
+ public:
+  BaseVariableObserverRemover() : calls_(0) {}
+
+  void ValueChanged(BaseVariable* variable) override {
+    for (auto& observer : remove_observers_) {
+      variable->RemoveObserver(observer);
+    }
+    calls_++;
+  }
+
+  void OnCallRemoveObserver(BaseVariable::ObserverInterface* observer) {
+    remove_observers_.push_back(observer);
+  }
+
+  int get_calls() { return calls_; }
+
+ private:
+  vector<BaseVariable::ObserverInterface*> remove_observers_;
+  int calls_;
+};
+
+// Tests that we can remove an observer from a Variable on the ValueChanged()
+// call to that observer.
+TEST_F(UmBaseVariableTest, NotifyValueRemovesObserversTest) {
+  DefaultVariable<int> var("var", kVariableModeAsync);
+  BaseVariableObserverRemover observer1;
+  BaseVariableObserverRemover observer2;
+
+  var.AddObserver(&observer1);
+  var.AddObserver(&observer2);
+
+  // Make each observer remove both observers on ValueChanged.
+  observer1.OnCallRemoveObserver(&observer1);
+  observer1.OnCallRemoveObserver(&observer2);
+  observer2.OnCallRemoveObserver(&observer1);
+  observer2.OnCallRemoveObserver(&observer2);
+
+  var.NotifyValueChanged();
+  MessageLoopRunMaxIterations(MessageLoop::current(), 100);
+
+  EXPECT_EQ(1, observer1.get_calls() + observer2.get_calls());
+}
+
+}  // namespace chromeos_update_manager
diff --git a/update_metadata.proto b/update_metadata.proto
new file mode 100644
index 0000000..c856405
--- /dev/null
+++ b/update_metadata.proto
@@ -0,0 +1,277 @@
+//
+// Copyright (C) 2010 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.
+//
+
+// Update file format: A delta update file contains all the deltas needed
+// to update a system from one specific version to another specific
+// version. The update format is represented by this struct pseudocode:
+// struct delta_update_file {
+//   char magic[4] = "CrAU";
+//   uint64 file_format_version;
+//   uint64 manifest_size;  // Size of protobuf DeltaArchiveManifest
+//
+//   // Only present if format_version > 1:
+//   uint32 metadata_signature_size;
+//
+//   // The Bzip2 compressed DeltaArchiveManifest
+//   char manifest[];
+//
+//   // The signature of the metadata (from the beginning of the payload up to
+//   // this location, not including the signature itself). This is a serialized
+//   // Signatures message.
+//   char medatada_signature_message[metadata_signature_size];
+//
+//   // Data blobs for files, no specific format. The specific offset
+//   // and length of each data blob is recorded in the DeltaArchiveManifest.
+//   struct {
+//     char data[];
+//   } blobs[];
+//
+//   // These two are not signed:
+//   uint64 payload_signatures_message_size;
+//   char payload_signatures_message[];
+//
+// };
+
+// The DeltaArchiveManifest protobuf is an ordered list of InstallOperation
+// objects. These objects are stored in a linear array in the
+// DeltaArchiveManifest. Each operation is applied in order by the client.
+
+// The DeltaArchiveManifest also contains the initial and final
+// checksums for the device.
+
+// The client will perform each InstallOperation in order, beginning even
+// before the entire delta file is downloaded (but after at least the
+// protobuf is downloaded). The types of operations are explained:
+// - REPLACE: Replace the dst_extents on the drive with the attached data,
+//   zero padding out to block size.
+// - REPLACE_BZ: bzip2-uncompress the attached data and write it into
+//   dst_extents on the drive, zero padding to block size.
+// - MOVE: Copy the data in src_extents to dst_extents. Extents may overlap,
+//   so it may be desirable to read all src_extents data into memory before
+//   writing it out.
+// - SOURCE_COPY: Copy the data in src_extents in the old partition to
+//   dst_extents in the new partition. There's no overlapping of data because
+//   the extents are in different partitions.
+// - BSDIFF: Read src_length bytes from src_extents into memory, perform
+//   bspatch with attached data, write new data to dst_extents, zero padding
+//   to block size.
+// - SOURCE_BSDIFF: Read the data in src_extents in the old partition, perform
+//   bspatch with the attached data and write the new data to dst_extents in the
+//   new partition.
+// - ZERO: Write zeros to the destination dst_extents.
+// - DISCARD: Discard the destination dst_extents blocks on the physical medium.
+//   the data read from those block is undefined.
+// - REPLACE_XZ: Replace the dst_extents with the contents of the attached
+//   xz file after decompression. The xz file should only use crc32 or no crc at
+//   all to be compatible with xz-embedded.
+//
+// The operations allowed in the payload (supported by the client) depend on the
+// major and minor version. See InstallOperation.Type bellow for details.
+
+package chromeos_update_engine;
+option optimize_for = LITE_RUNTIME;
+
+// Data is packed into blocks on disk, always starting from the beginning
+// of the block. If a file's data is too large for one block, it overflows
+// into another block, which may or may not be the following block on the
+// physical partition. An ordered list of extents is another
+// representation of an ordered list of blocks. For example, a file stored
+// in blocks 9, 10, 11, 2, 18, 12 (in that order) would be stored in
+// extents { {9, 3}, {2, 1}, {18, 1}, {12, 1} } (in that order).
+// In general, files are stored sequentially on disk, so it's more efficient
+// to use extents to encode the block lists (this is effectively
+// run-length encoding).
+// A sentinel value (kuint64max) as the start block denotes a sparse-hole
+// in a file whose block-length is specified by num_blocks.
+
+// Signatures: Updates may be signed by the OS vendor. The client verifies
+// an update's signature by hashing the entire download. The section of the
+// download that contains the signature is at the end of the file, so when
+// signing a file, only the part up to the signature part is signed.
+// Then, the client looks inside the download's Signatures message for a
+// Signature message that it knows how to handle. Generally, a client will
+// only know how to handle one type of signature, but an update may contain
+// many signatures to support many different types of client. Then client
+// selects a Signature message and uses that, along with a known public key,
+// to verify the download. The public key is expected to be part of the
+// client.
+
+message Extent {
+  optional uint64 start_block = 1;
+  optional uint64 num_blocks = 2;
+}
+
+message Signatures {
+  message Signature {
+    optional uint32 version = 1;
+    optional bytes data = 2;
+  }
+  repeated Signature signatures = 1;
+}
+
+message PartitionInfo {
+  optional uint64 size = 1;
+  optional bytes hash = 2;
+}
+
+// Describe an image we are based on in a human friendly way.
+// Examples:
+//   dev-channel, x86-alex, 1.2.3, mp-v3
+//   nplusone-channel, x86-alex, 1.2.4, mp-v3, dev-channel, 1.2.3
+//
+// All fields will be set, if this message is present.
+message ImageInfo {
+  optional string board = 1;
+  optional string key = 2;
+  optional string channel = 3;
+  optional string version = 4;
+
+  // If these values aren't present, they should be assumed to match
+  // the equivalent value above. They are normally only different for
+  // special image types such as nplusone images.
+  optional string build_channel = 5;
+  optional string build_version = 6;
+}
+
+message InstallOperation {
+  enum Type {
+    REPLACE = 0;  // Replace destination extents w/ attached data
+    REPLACE_BZ = 1;  // Replace destination extents w/ attached bzipped data
+    MOVE = 2;  // Move source extents to destination extents
+    BSDIFF = 3;  // The data is a bsdiff binary diff
+
+    // On minor version 2 or newer, these operations are supported:
+    SOURCE_COPY = 4; // Copy from source to target partition
+    SOURCE_BSDIFF = 5; // Like BSDIFF, but read from source partition
+
+    // On minor version 3 or newer and on major version 2 or newer, these
+    // operations are supported:
+    ZERO = 6;  // Write zeros in the destination.
+    DISCARD = 7;  // Discard the destination blocks, reading as undefined.
+    REPLACE_XZ = 8; // Replace destination extents w/ attached xz data.
+  }
+  required Type type = 1;
+  // The offset into the delta file (after the protobuf)
+  // where the data (if any) is stored
+  optional uint32 data_offset = 2;
+  // The length of the data in the delta file
+  optional uint32 data_length = 3;
+
+  // Ordered list of extents that are read from (if any) and written to.
+  repeated Extent src_extents = 4;
+  // Byte length of src, equal to the number of blocks in src_extents *
+  // block_size. It is used for BSDIFF, because we need to pass that
+  // external program the number of bytes to read from the blocks we pass it.
+  // This is not used in any other operation.
+  optional uint64 src_length = 5;
+
+  repeated Extent dst_extents = 6;
+  // Byte length of dst, equal to the number of blocks in dst_extents *
+  // block_size. Used for BSDIFF, but not in any other operation.
+  optional uint64 dst_length = 7;
+
+  // Optional SHA 256 hash of the blob associated with this operation.
+  // This is used as a primary validation for http-based downloads and
+  // as a defense-in-depth validation for https-based downloads. If
+  // the operation doesn't refer to any blob, this field will have
+  // zero bytes.
+  optional bytes data_sha256_hash = 8;
+
+  // Indicates the SHA 256 hash of the source data referenced in src_extents at
+  // the time of applying the operation. If present, the update_engine daemon
+  // MUST read and verify the source data before applying the operation.
+  optional bytes src_sha256_hash = 9;
+}
+
+// Describes the update to apply to a single partition.
+message PartitionUpdate {
+  // A platform-specific name to identify the partition set being updated. For
+  // example, in Chrome OS this could be "ROOT" or "KERNEL".
+  required string partition_name = 1;
+
+  // Whether this partition carries a filesystem with post-install program that
+  // must be run to finalize the update process. See also |postinstall_path| and
+  // |filesystem_type|.
+  optional bool run_postinstall = 2;
+
+  // The path of the executable program to run during the post-install step,
+  // relative to the root of this filesystem. If not set, the default "postinst"
+  // will be used. This setting is only used when |run_postinstall| is set and
+  // true.
+  optional string postinstall_path = 3;
+
+  // The filesystem type as passed to the mount(2) syscall when mounting the new
+  // filesystem to run the post-install program. If not set, a fixed list of
+  // filesystems will be attempted. This setting is only used if
+  // |run_postinstall| is set and true.
+  optional string filesystem_type = 4;
+
+  // If present, a list of signatures of the new_partition_info.hash signed with
+  // different keys. If the update_engine daemon requires vendor-signed images
+  // and has its public key installed, one of the signatures should be valid
+  // for /postinstall to run.
+  repeated Signatures.Signature new_partition_signature = 5;
+
+  optional PartitionInfo old_partition_info = 6;
+  optional PartitionInfo new_partition_info = 7;
+
+  // The list of operations to be performed to apply this PartitionUpdate. The
+  // associated operation blobs (in operations[i].data_offset, data_length)
+  // should be stored contiguously and in the same order.
+  repeated InstallOperation operations = 8;
+}
+
+message DeltaArchiveManifest {
+  // Only present in major version = 1. List of install operations for the
+  // kernel and rootfs partitions. For major version = 2 see the |partitions|
+  // field.
+  repeated InstallOperation install_operations = 1;
+  repeated InstallOperation kernel_install_operations = 2;
+
+  // (At time of writing) usually 4096
+  optional uint32 block_size = 3 [default = 4096];
+
+  // If signatures are present, the offset into the blobs, generally
+  // tacked onto the end of the file, and the length. We use an offset
+  // rather than a bool to allow for more flexibility in future file formats.
+  // If either is absent, it means signatures aren't supported in this
+  // file.
+  optional uint64 signatures_offset = 4;
+  optional uint64 signatures_size = 5;
+
+  // Only present in major version = 1. Partition metadata used to validate the
+  // update. For major version = 2 see the |partitions| field.
+  optional PartitionInfo old_kernel_info = 6;
+  optional PartitionInfo new_kernel_info = 7;
+  optional PartitionInfo old_rootfs_info = 8;
+  optional PartitionInfo new_rootfs_info = 9;
+
+  // old_image_info will only be present for delta images.
+  optional ImageInfo old_image_info = 10;
+
+  optional ImageInfo new_image_info = 11;
+
+  // The minor version, also referred as "delta version", of the payload.
+  optional uint32 minor_version = 12 [default = 0];
+
+  // Only present in major version >= 2. List of partitions that will be
+  // updated, in the order they will be updated. This field replaces the
+  // |install_operations|, |kernel_install_operations| and the
+  // |{old,new}_{kernel,rootfs}_info| fields used in major version = 1. This
+  // array can have more than two partitions if needed, and they are identified
+  // by the partition name.
+  repeated PartitionUpdate partitions = 13;
+}
diff --git a/update_payload_key/README b/update_payload_key/README
new file mode 100644
index 0000000..cf87148
--- /dev/null
+++ b/update_payload_key/README
@@ -0,0 +1,2 @@
+This directory contains the public half of the payload signing key. This is
+baked into the system image as part of update_engine install.
diff --git a/update_payload_key/brillo-update-payload-key.pub.pem b/update_payload_key/brillo-update-payload-key.pub.pem
new file mode 100644
index 0000000..7e5164c
--- /dev/null
+++ b/update_payload_key/brillo-update-payload-key.pub.pem
@@ -0,0 +1,9 @@
+-----BEGIN PUBLIC KEY-----
+MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxAxPqfII4vIe3cqKzdvl
+gwjBhj9kyF+6ig73yZq0o4wLOq3nsRUToaIOtQmcjr1G+hhSXBU3WTbfZLlm07Fb
+B535o2zhYghs8Br7xobjX+gikEnxnFuTtB2sB4Gpan4hKwU+BuZhJDSl1oZwUJJ4
+eiGJpH5xJswbyO/bA81BCMjU3rm+G6SzOLQTK0YEnhn7bB69UucM57GM7l+dCl8r
+RhKjbpP7E1fVtgX++BGs6pKciPLxYfXVup0MgH0h8VdSDMiHkshIXYvcCV1KOBFX
+9GrYvXLtq41Hm5hC5l48mwLi0ALdIfbPQ5oHLl2u+etLmGwbMpzhybTCZQA/SgEl
+HwIDAQAB
+-----END PUBLIC KEY-----
diff --git a/update_status_utils.cc b/update_status_utils.cc
new file mode 100644
index 0000000..ff039b8
--- /dev/null
+++ b/update_status_utils.cc
@@ -0,0 +1,89 @@
+//
+// Copyright (C) 2015 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 "update_engine/update_status_utils.h"
+
+#include <base/logging.h>
+#include <update_engine/dbus-constants.h>
+
+using update_engine::UpdateStatus;
+
+namespace chromeos_update_engine {
+
+const char* UpdateStatusToString(const UpdateStatus& status) {
+  switch (status) {
+    case UpdateStatus::IDLE:
+      return update_engine::kUpdateStatusIdle;
+    case UpdateStatus::CHECKING_FOR_UPDATE:
+      return update_engine::kUpdateStatusCheckingForUpdate;
+    case UpdateStatus::UPDATE_AVAILABLE:
+      return update_engine::kUpdateStatusUpdateAvailable;
+    case UpdateStatus::DOWNLOADING:
+      return update_engine::kUpdateStatusDownloading;
+    case UpdateStatus::VERIFYING:
+      return update_engine::kUpdateStatusVerifying;
+    case UpdateStatus::FINALIZING:
+      return update_engine::kUpdateStatusFinalizing;
+    case UpdateStatus::UPDATED_NEED_REBOOT:
+      return update_engine::kUpdateStatusUpdatedNeedReboot;
+    case UpdateStatus::REPORTING_ERROR_EVENT:
+      return update_engine::kUpdateStatusReportingErrorEvent;
+    case UpdateStatus::ATTEMPTING_ROLLBACK:
+      return update_engine::kUpdateStatusAttemptingRollback;
+    case UpdateStatus::DISABLED:
+      return update_engine::kUpdateStatusDisabled;
+  }
+
+  NOTREACHED();
+  return nullptr;
+}
+
+bool StringToUpdateStatus(const std::string& s,
+                          UpdateStatus* status) {
+  if (s == update_engine::kUpdateStatusIdle) {
+    *status = UpdateStatus::IDLE;
+    return true;
+  } else if (s == update_engine::kUpdateStatusCheckingForUpdate) {
+    *status = UpdateStatus::CHECKING_FOR_UPDATE;
+    return true;
+  } else if (s == update_engine::kUpdateStatusUpdateAvailable) {
+    *status = UpdateStatus::UPDATE_AVAILABLE;
+    return true;
+  } else if (s == update_engine::kUpdateStatusDownloading) {
+    *status = UpdateStatus::DOWNLOADING;
+    return true;
+  } else if (s == update_engine::kUpdateStatusVerifying) {
+    *status = UpdateStatus::VERIFYING;
+    return true;
+  } else if (s == update_engine::kUpdateStatusFinalizing) {
+    *status = UpdateStatus::FINALIZING;
+    return true;
+  } else if (s == update_engine::kUpdateStatusUpdatedNeedReboot) {
+    *status = UpdateStatus::UPDATED_NEED_REBOOT;
+    return true;
+  } else if (s == update_engine::kUpdateStatusReportingErrorEvent) {
+    *status = UpdateStatus::REPORTING_ERROR_EVENT;
+    return true;
+  } else if (s == update_engine::kUpdateStatusAttemptingRollback) {
+    *status = UpdateStatus::ATTEMPTING_ROLLBACK;
+    return true;
+  } else if (s == update_engine::kUpdateStatusDisabled) {
+    *status = UpdateStatus::DISABLED;
+    return true;
+  }
+  return false;
+}
+
+}  // namespace chromeos_update_engine
diff --git a/update_status_utils.h b/update_status_utils.h
new file mode 100644
index 0000000..30ae53b
--- /dev/null
+++ b/update_status_utils.h
@@ -0,0 +1,33 @@
+//
+// Copyright (C) 2015 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.
+//
+
+#ifndef UPDATE_ENGINE_UPDATE_STATUS_UTILS_H_
+#define UPDATE_ENGINE_UPDATE_STATUS_UTILS_H_
+
+#include <string>
+
+#include "update_engine/client_library/include/update_engine/update_status.h"
+
+namespace chromeos_update_engine {
+
+const char* UpdateStatusToString(const update_engine::UpdateStatus& status);
+
+bool StringToUpdateStatus(const std::string& update_status_as_string,
+                          update_engine::UpdateStatus* status);
+
+}  // namespace chromeos_update_engine
+
+#endif  // UPDATE_ENGINE_UPDATE_STATUS_UTILS_H_
