diff --git a/DEPS b/DEPS
index 24e59e9..d54d5a6 100644
--- a/DEPS
+++ b/DEPS
@@ -39,11 +39,11 @@
   # Three lines of non-changing comments so that
   # the commit queue can handle CLs rolling Skia
   # and whatever else without interference from each other.
-  'skia_revision': 'e82a6c7e71090c218e773fd2f7af6622490d892a',
+  'skia_revision': 'ad38ed6003ad89a21e40d76987db4bba7d42f3d0',
   # Three lines of non-changing comments so that
   # the commit queue can handle CLs rolling V8
   # and whatever else without interference from each other.
-  'v8_revision': '15058271dadb1064c0e053511de14ac0c6865853',
+  'v8_revision': '987c0e0d09f0d33c8ebaa902c1e4d52dd82adbe5',
   # Three lines of non-changing comments so that
   # the commit queue can handle CLs rolling swarming_client
   # and whatever else without interference from each other.
diff --git a/base/BUILD.gn b/base/BUILD.gn
index 3f8380c7..60821ee 100644
--- a/base/BUILD.gn
+++ b/base/BUILD.gn
@@ -1465,85 +1465,6 @@
   }
 }
 
-component("prefs") {
-  sources = [
-    "prefs/default_pref_store.cc",
-    "prefs/default_pref_store.h",
-    "prefs/json_pref_store.cc",
-    "prefs/json_pref_store.h",
-    "prefs/overlay_user_pref_store.cc",
-    "prefs/overlay_user_pref_store.h",
-    "prefs/pref_change_registrar.cc",
-    "prefs/pref_change_registrar.h",
-    "prefs/pref_member.cc",
-    "prefs/pref_member.h",
-    "prefs/pref_notifier_impl.cc",
-    "prefs/pref_notifier_impl.h",
-    "prefs/pref_registry.cc",
-    "prefs/pref_registry.h",
-    "prefs/pref_registry_simple.cc",
-    "prefs/pref_registry_simple.h",
-    "prefs/pref_service.cc",
-    "prefs/pref_service.h",
-    "prefs/pref_service_factory.cc",
-    "prefs/pref_service_factory.h",
-    "prefs/pref_store.cc",
-    "prefs/pref_store.h",
-    "prefs/pref_value_map.cc",
-    "prefs/pref_value_map.h",
-    "prefs/pref_value_store.cc",
-    "prefs/pref_value_store.h",
-    "prefs/scoped_user_pref_update.cc",
-    "prefs/scoped_user_pref_update.h",
-    "prefs/value_map_pref_store.cc",
-    "prefs/value_map_pref_store.h",
-  ]
-  if (!is_ios) {
-    sources += [
-      "prefs/base_prefs_export.h",
-      "prefs/persistent_pref_store.h",
-      "prefs/pref_filter.h",
-      "prefs/pref_notifier.h",
-      "prefs/pref_observer.h",
-      "prefs/writeable_pref_store.h",
-    ]
-  }
-
-  defines = [ "BASE_PREFS_IMPLEMENTATION" ]
-
-  deps = [
-    ":base",
-  ]
-
-  if (!is_debug) {
-    configs -= [ "//build/config/compiler:default_optimization" ]
-    configs += [ "//build/config/compiler:optimize_max" ]
-  }
-}
-
-source_set("prefs_test_support") {
-  testonly = true
-  sources = [
-    "prefs/mock_pref_change_callback.cc",
-    "prefs/mock_pref_change_callback.h",
-    "prefs/pref_store_observer_mock.cc",
-    "prefs/pref_store_observer_mock.h",
-    "prefs/testing_pref_service.cc",
-    "prefs/testing_pref_service.h",
-    "prefs/testing_pref_store.cc",
-    "prefs/testing_pref_store.h",
-  ]
-
-  public_deps = [
-    ":prefs",
-  ]
-  deps = [
-    ":base",
-    "//testing/gmock",
-    "//testing/gtest",
-  ]
-}
-
 source_set("message_loop_tests") {
   testonly = true
   sources = [
@@ -1731,16 +1652,6 @@
     "posix/file_descriptor_shuffle_unittest.cc",
     "posix/unix_domain_socket_linux_unittest.cc",
     "power_monitor/power_monitor_unittest.cc",
-    "prefs/default_pref_store_unittest.cc",
-    "prefs/json_pref_store_unittest.cc",
-    "prefs/overlay_user_pref_store_unittest.cc",
-    "prefs/pref_change_registrar_unittest.cc",
-    "prefs/pref_member_unittest.cc",
-    "prefs/pref_notifier_impl_unittest.cc",
-    "prefs/pref_service_unittest.cc",
-    "prefs/pref_value_map_unittest.cc",
-    "prefs/pref_value_store_unittest.cc",
-    "prefs/scoped_user_pref_update_unittest.cc",
     "process/memory_unittest.cc",
     "process/memory_unittest_mac.h",
     "process/memory_unittest_mac.mm",
@@ -1860,8 +1771,6 @@
     ":base",
     ":i18n",
     ":message_loop_tests",
-    ":prefs",
-    ":prefs_test_support",
     "//base/test:run_all_unittests",
     "//base/test:test_support",
     "//base/third_party/dynamic_annotations",
diff --git a/base/base.gyp b/base/base.gyp
index bc315b69..929a3e4 100644
--- a/base/base.gyp
+++ b/base/base.gyp
@@ -312,82 +312,6 @@
       ],
     },
     {
-      'target_name': 'base_prefs',
-      'type': '<(component)',
-      'variables': {
-        'enable_wexit_time_destructors': 1,
-        'optimize': 'max',
-      },
-      'dependencies': [
-        'base',
-      ],
-      'export_dependent_settings': [
-        'base',
-      ],
-      'defines': [
-        'BASE_PREFS_IMPLEMENTATION',
-      ],
-      'sources': [
-        'prefs/base_prefs_export.h',
-        'prefs/default_pref_store.cc',
-        'prefs/default_pref_store.h',
-        'prefs/json_pref_store.cc',
-        'prefs/json_pref_store.h',
-        'prefs/overlay_user_pref_store.cc',
-        'prefs/overlay_user_pref_store.h',
-        'prefs/persistent_pref_store.h',
-        'prefs/pref_change_registrar.cc',
-        'prefs/pref_change_registrar.h',
-        'prefs/pref_filter.h',
-        'prefs/pref_member.cc',
-        'prefs/pref_member.h',
-        'prefs/pref_notifier.h',
-        'prefs/pref_notifier_impl.cc',
-        'prefs/pref_notifier_impl.h',
-        'prefs/pref_observer.h',
-        'prefs/pref_registry.cc',
-        'prefs/pref_registry.h',
-        'prefs/pref_registry_simple.cc',
-        'prefs/pref_registry_simple.h',
-        'prefs/pref_service.cc',
-        'prefs/pref_service.h',
-        'prefs/pref_service_factory.cc',
-        'prefs/pref_service_factory.h',
-        'prefs/pref_store.cc',
-        'prefs/pref_store.h',
-        'prefs/pref_value_map.cc',
-        'prefs/pref_value_map.h',
-        'prefs/pref_value_store.cc',
-        'prefs/pref_value_store.h',
-        'prefs/scoped_user_pref_update.cc',
-        'prefs/scoped_user_pref_update.h',
-        'prefs/value_map_pref_store.cc',
-        'prefs/value_map_pref_store.h',
-        'prefs/writeable_pref_store.h',
-      ],
-      'includes': [
-        '../build/android/increase_size_for_speed.gypi',
-      ],
-    },
-    {
-      'target_name': 'base_prefs_test_support',
-      'type': 'static_library',
-      'dependencies': [
-        'base',
-        'base_prefs',
-        '../testing/gmock.gyp:gmock',
-      ],
-      'sources': [
-        'prefs/mock_pref_change_callback.cc',
-        'prefs/pref_store_observer_mock.cc',
-        'prefs/pref_store_observer_mock.h',
-        'prefs/testing_pref_service.cc',
-        'prefs/testing_pref_service.h',
-        'prefs/testing_pref_store.cc',
-        'prefs/testing_pref_store.h',
-      ],
-    },
-    {
       # This is the subset of files from base that should not be used with a
       # dynamic library. Note that this library cannot depend on base because
       # base depends on base_static.
@@ -566,17 +490,6 @@
         'posix/file_descriptor_shuffle_unittest.cc',
         'posix/unix_domain_socket_linux_unittest.cc',
         'power_monitor/power_monitor_unittest.cc',
-        'prefs/default_pref_store_unittest.cc',
-        'prefs/json_pref_store_unittest.cc',
-        'prefs/mock_pref_change_callback.h',
-        'prefs/overlay_user_pref_store_unittest.cc',
-        'prefs/pref_change_registrar_unittest.cc',
-        'prefs/pref_member_unittest.cc',
-        'prefs/pref_notifier_impl_unittest.cc',
-        'prefs/pref_service_unittest.cc',
-        'prefs/pref_value_map_unittest.cc',
-        'prefs/pref_value_store_unittest.cc',
-        'prefs/scoped_user_pref_update_unittest.cc',
         'process/memory_unittest.cc',
         'process/memory_unittest_mac.h',
         'process/memory_unittest_mac.mm',
@@ -678,8 +591,6 @@
         'base',
         'base_i18n',
         'base_message_loop_tests',
-        'base_prefs',
-        'base_prefs_test_support',
         'base_static',
         'run_all_unittests',
         'test_support_base',
diff --git a/base/prefs/DEPS b/base/prefs/DEPS
new file mode 100644
index 0000000..2edd44e
--- /dev/null
+++ b/base/prefs/DEPS
@@ -0,0 +1,4 @@
+# TODO(brettw) remove this when prefs is completely moved to components.
+include_rules = [
+  "+components/prefs",
+]
diff --git a/base/prefs/README b/base/prefs/README
deleted file mode 100644
index 52d9c43e..0000000
--- a/base/prefs/README
+++ /dev/null
@@ -1,6 +0,0 @@
-Prefs is a general-purpose key-value store for application preferences.
-
-The Prefs code lives in base/prefs but is not part of the
-'base/base.gyp:base' library because of a desire to keep its use
-optional. If you use Prefs, you should add a GYP dependency on
-base/base.gyp:base_prefs.
diff --git a/base/prefs/base_prefs_export.h b/base/prefs/base_prefs_export.h
index 3d207db..477e1aa 100644
--- a/base/prefs/base_prefs_export.h
+++ b/base/prefs/base_prefs_export.h
@@ -2,28 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_BASE_PREFS_EXPORT_H_
-#define BASE_PREFS_BASE_PREFS_EXPORT_H_
-
-#if defined(COMPONENT_BUILD)
-#if defined(WIN32)
-
-#if defined(BASE_PREFS_IMPLEMENTATION)
-#define BASE_PREFS_EXPORT __declspec(dllexport)
-#else
-#define BASE_PREFS_EXPORT __declspec(dllimport)
-#endif  // defined(BASE_PREFS_IMPLEMENTATION)
-
-#else  // defined(WIN32)
-#if defined(BASE_PREFS_IMPLEMENTATION)
-#define BASE_PREFS_EXPORT __attribute__((visibility("default")))
-#else
-#define BASE_PREFS_EXPORT
-#endif
-#endif
-
-#else  // defined(COMPONENT_BUILD)
-#define BASE_PREFS_EXPORT
-#endif
-
-#endif  // BASE_PREFS_BASE_PREFS_EXPORT_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/base_prefs_export.h"
diff --git a/base/prefs/default_pref_store.h b/base/prefs/default_pref_store.h
index ac5364d..e590bf8 100644
--- a/base/prefs/default_pref_store.h
+++ b/base/prefs/default_pref_store.h
@@ -2,52 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_DEFAULT_PREF_STORE_H_
-#define BASE_PREFS_DEFAULT_PREF_STORE_H_
-
-#include <string>
-
-#include "base/macros.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_store.h"
-#include "base/prefs/pref_value_map.h"
-#include "base/values.h"
-
-// Used within a PrefRegistry to keep track of default preference values.
-class BASE_PREFS_EXPORT DefaultPrefStore : public PrefStore {
- public:
-  typedef PrefValueMap::const_iterator const_iterator;
-
-  DefaultPrefStore();
-
-  // PrefStore implementation:
-  bool GetValue(const std::string& key,
-                const base::Value** result) const override;
-  void AddObserver(PrefStore::Observer* observer) override;
-  void RemoveObserver(PrefStore::Observer* observer) override;
-  bool HasObservers() const override;
-
-  // Sets a |value| for |key|. Should only be called if a value has not been
-  // set yet; otherwise call ReplaceDefaultValue().
-  void SetDefaultValue(const std::string& key, scoped_ptr<base::Value> value);
-
-  // Replaces the the value for |key| with a new value. Should only be called
-  // if a value has alreday been set; otherwise call SetDefaultValue().
-  void ReplaceDefaultValue(const std::string& key,
-                           scoped_ptr<base::Value> value);
-
-  const_iterator begin() const;
-  const_iterator end() const;
-
- private:
-  ~DefaultPrefStore() override;
-
-  PrefValueMap prefs_;
-
-  base::ObserverList<PrefStore::Observer, true> observers_;
-
-  DISALLOW_COPY_AND_ASSIGN(DefaultPrefStore);
-};
-
-#endif  // BASE_PREFS_DEFAULT_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/default_pref_store.h"
diff --git a/base/prefs/json_pref_store.h b/base/prefs/json_pref_store.h
index 6342977..247102f 100644
--- a/base/prefs/json_pref_store.h
+++ b/base/prefs/json_pref_store.h
@@ -2,228 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_JSON_PREF_STORE_H_
-#define BASE_PREFS_JSON_PREF_STORE_H_
-
-#include <stdint.h>
-
-#include <set>
-#include <string>
-
-#include "base/callback_forward.h"
-#include "base/compiler_specific.h"
-#include "base/files/file_path.h"
-#include "base/files/important_file_writer.h"
-#include "base/gtest_prod_util.h"
-#include "base/macros.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/memory/weak_ptr.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/persistent_pref_store.h"
-#include "base/threading/non_thread_safe.h"
-
-class PrefFilter;
-
-namespace base {
-class Clock;
-class DictionaryValue;
-class FilePath;
-class HistogramBase;
-class JsonPrefStoreLossyWriteTest;
-class SequencedTaskRunner;
-class SequencedWorkerPool;
-class Value;
-FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestBasic);
-FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestSinglePeriod);
-FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestMultiplePeriods);
-FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestPeriodWithGaps);
-}
-
-// A writable PrefStore implementation that is used for user preferences.
-class BASE_PREFS_EXPORT JsonPrefStore
-    : public PersistentPrefStore,
-      public base::ImportantFileWriter::DataSerializer,
-      public base::SupportsWeakPtr<JsonPrefStore>,
-      public base::NonThreadSafe {
- public:
-  struct ReadResult;
-
-  // Returns instance of SequencedTaskRunner which guarantees that file
-  // operations on the same file will be executed in sequenced order.
-  static scoped_refptr<base::SequencedTaskRunner> GetTaskRunnerForFile(
-      const base::FilePath& pref_filename,
-      base::SequencedWorkerPool* worker_pool);
-
-  // Same as the constructor below with no alternate filename.
-  JsonPrefStore(
-      const base::FilePath& pref_filename,
-      const scoped_refptr<base::SequencedTaskRunner>& sequenced_task_runner,
-      scoped_ptr<PrefFilter> pref_filter);
-
-  // |sequenced_task_runner| must be a shutdown-blocking task runner, ideally
-  // created by the GetTaskRunnerForFile() method above.
-  // |pref_filename| is the path to the file to read prefs from.
-  // |pref_alternate_filename| is the path to an alternate file which the
-  // desired prefs may have previously been written to. If |pref_filename|
-  // doesn't exist and |pref_alternate_filename| does, |pref_alternate_filename|
-  // will be moved to |pref_filename| before the read occurs.
-  JsonPrefStore(
-      const base::FilePath& pref_filename,
-      const base::FilePath& pref_alternate_filename,
-      const scoped_refptr<base::SequencedTaskRunner>& sequenced_task_runner,
-      scoped_ptr<PrefFilter> pref_filter);
-
-  // PrefStore overrides:
-  bool GetValue(const std::string& key,
-                const base::Value** result) const override;
-  void AddObserver(PrefStore::Observer* observer) override;
-  void RemoveObserver(PrefStore::Observer* observer) override;
-  bool HasObservers() const override;
-  bool IsInitializationComplete() const override;
-
-  // PersistentPrefStore overrides:
-  bool GetMutableValue(const std::string& key, base::Value** result) override;
-  void SetValue(const std::string& key,
-                scoped_ptr<base::Value> value,
-                uint32_t flags) override;
-  void SetValueSilently(const std::string& key,
-                        scoped_ptr<base::Value> value,
-                        uint32_t flags) override;
-  void RemoveValue(const std::string& key, uint32_t flags) override;
-  bool ReadOnly() const override;
-  PrefReadError GetReadError() const override;
-  // Note this method may be asynchronous if this instance has a |pref_filter_|
-  // in which case it will return PREF_READ_ERROR_ASYNCHRONOUS_TASK_INCOMPLETE.
-  // See details in pref_filter.h.
-  PrefReadError ReadPrefs() override;
-  void ReadPrefsAsync(ReadErrorDelegate* error_delegate) override;
-  void CommitPendingWrite() override;
-  void SchedulePendingLossyWrites() override;
-  void ReportValueChanged(const std::string& key, uint32_t flags) override;
-
-  // Just like RemoveValue(), but doesn't notify observers. Used when doing some
-  // cleanup that shouldn't otherwise alert observers.
-  void RemoveValueSilently(const std::string& key, uint32_t flags);
-
-  // Registers |on_next_successful_write| to be called once, on the next
-  // successful write event of |writer_|.
-  void RegisterOnNextSuccessfulWriteCallback(
-      const base::Closure& on_next_successful_write);
-
- private:
-  // Represents a histogram for recording the number of writes to the pref file
-  // that occur every kHistogramWriteReportIntervalInMins minutes.
-  class BASE_PREFS_EXPORT WriteCountHistogram {
-   public:
-    static const int32_t kHistogramWriteReportIntervalMins;
-
-    WriteCountHistogram(const base::TimeDelta& commit_interval,
-                        const base::FilePath& path);
-    // Constructor for testing. |clock| is a test Clock that is used to retrieve
-    // the time.
-    WriteCountHistogram(const base::TimeDelta& commit_interval,
-                        const base::FilePath& path,
-                        scoped_ptr<base::Clock> clock);
-    ~WriteCountHistogram();
-
-    // Record that a write has occured.
-    void RecordWriteOccured();
-
-    // Reports writes (that have not yet been reported) in all of the recorded
-    // intervals that have elapsed up until current time.
-    void ReportOutstandingWrites();
-
-    base::HistogramBase* GetHistogram();
-
-   private:
-    // The minimum interval at which writes can occur.
-    const base::TimeDelta commit_interval_;
-
-    // The path to the file.
-    const base::FilePath path_;
-
-    // Clock which is used to retrieve the current time.
-    scoped_ptr<base::Clock> clock_;
-
-    // The interval at which to report write counts.
-    const base::TimeDelta report_interval_;
-
-    // The time at which the last histogram value was reported for the number
-    // of write counts.
-    base::Time last_report_time_;
-
-    // The number of writes that have occured since the last write count was
-    // reported.
-    uint32_t writes_since_last_report_;
-
-    DISALLOW_COPY_AND_ASSIGN(WriteCountHistogram);
-  };
-
-  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
-                           WriteCountHistogramTestBasic);
-  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
-                           WriteCountHistogramTestSinglePeriod);
-  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
-                           WriteCountHistogramTestMultiplePeriods);
-  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
-                           WriteCountHistogramTestPeriodWithGaps);
-  friend class base::JsonPrefStoreLossyWriteTest;
-
-  ~JsonPrefStore() override;
-
-  // This method is called after the JSON file has been read.  It then hands
-  // |value| (or an empty dictionary in some read error cases) to the
-  // |pref_filter| if one is set. It also gives a callback pointing at
-  // FinalizeFileRead() to that |pref_filter_| which is then responsible for
-  // invoking it when done. If there is no |pref_filter_|, FinalizeFileRead()
-  // is invoked directly.
-  void OnFileRead(scoped_ptr<ReadResult> read_result);
-
-  // ImportantFileWriter::DataSerializer overrides:
-  bool SerializeData(std::string* output) override;
-
-  // This method is called after the JSON file has been read and the result has
-  // potentially been intercepted and modified by |pref_filter_|.
-  // |initialization_successful| is pre-determined by OnFileRead() and should
-  // be used when reporting OnInitializationCompleted().
-  // |schedule_write| indicates whether a write should be immediately scheduled
-  // (typically because the |pref_filter_| has already altered the |prefs|) --
-  // this will be ignored if this store is read-only.
-  void FinalizeFileRead(bool initialization_successful,
-                        scoped_ptr<base::DictionaryValue> prefs,
-                        bool schedule_write);
-
-  // Schedule a write with the file writer as long as |flags| doesn't contain
-  // WriteablePrefStore::LOSSY_PREF_WRITE_FLAG.
-  void ScheduleWrite(uint32_t flags);
-
-  const base::FilePath path_;
-  const base::FilePath alternate_path_;
-  const scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner_;
-
-  scoped_ptr<base::DictionaryValue> prefs_;
-
-  bool read_only_;
-
-  // Helper for safely writing pref data.
-  base::ImportantFileWriter writer_;
-
-  scoped_ptr<PrefFilter> pref_filter_;
-  base::ObserverList<PrefStore::Observer, true> observers_;
-
-  scoped_ptr<ReadErrorDelegate> error_delegate_;
-
-  bool initialized_;
-  bool filtering_in_progress_;
-  bool pending_lossy_write_;
-  PrefReadError read_error_;
-
-  std::set<std::string> keys_need_empty_value_;
-
-  WriteCountHistogram write_count_histogram_;
-
-  DISALLOW_COPY_AND_ASSIGN(JsonPrefStore);
-};
-
-#endif  // BASE_PREFS_JSON_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/json_pref_store.h"
diff --git a/base/prefs/mock_pref_change_callback.h b/base/prefs/mock_pref_change_callback.h
index 3030fab1..90ad29472 100644
--- a/base/prefs/mock_pref_change_callback.h
+++ b/base/prefs/mock_pref_change_callback.h
@@ -2,50 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
-#define BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
-
-#include <string>
-
-#include "base/prefs/pref_change_registrar.h"
-#include "base/prefs/pref_service.h"
-#include "testing/gmock/include/gmock/gmock.h"
-
-using testing::Pointee;
-using testing::Property;
-using testing::Truly;
-
-// Matcher that checks whether the current value of the preference named
-// |pref_name| in |prefs| matches |value|. If |value| is NULL, the matcher
-// checks that the value is not set.
-MATCHER_P3(PrefValueMatches, prefs, pref_name, value, "") {
-  const PrefService::Preference* pref = prefs->FindPreference(pref_name);
-  if (!pref)
-    return false;
-
-  const base::Value* actual_value = pref->GetValue();
-  if (!actual_value)
-    return value == NULL;
-  if (!value)
-    return actual_value == NULL;
-  return value->Equals(actual_value);
-}
-
-// A mock for testing preference notifications and easy setup of expectations.
-class MockPrefChangeCallback {
- public:
-  explicit MockPrefChangeCallback(PrefService* prefs);
-  virtual ~MockPrefChangeCallback();
-
-  PrefChangeRegistrar::NamedChangeCallback GetCallback();
-
-  MOCK_METHOD1(OnPreferenceChanged, void(const std::string&));
-
-  void Expect(const std::string& pref_name,
-              const base::Value* value);
-
- private:
-  PrefService* prefs_;
-};
-
-#endif  // BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/mock_pref_change_callback.h"
diff --git a/base/prefs/overlay_user_pref_store.h b/base/prefs/overlay_user_pref_store.h
index 35ada57..594c501 100644
--- a/base/prefs/overlay_user_pref_store.h
+++ b/base/prefs/overlay_user_pref_store.h
@@ -2,88 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
-#define BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
-
-#include <stdint.h>
-
-#include <map>
-#include <string>
-
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/persistent_pref_store.h"
-#include "base/prefs/pref_value_map.h"
-
-// PersistentPrefStore that directs all write operations into an in-memory
-// PrefValueMap. Read operations are first answered by the PrefValueMap.
-// If the PrefValueMap does not contain a value for the requested key,
-// the look-up is passed on to an underlying PersistentPrefStore |underlay_|.
-class BASE_PREFS_EXPORT OverlayUserPrefStore : public PersistentPrefStore,
-                                               public PrefStore::Observer {
- public:
-  explicit OverlayUserPrefStore(PersistentPrefStore* underlay);
-
-  // Returns true if a value has been set for the |key| in this
-  // OverlayUserPrefStore, i.e. if it potentially overrides a value
-  // from the |underlay_|.
-  virtual bool IsSetInOverlay(const std::string& key) const;
-
-  // Methods of PrefStore.
-  void AddObserver(PrefStore::Observer* observer) override;
-  void RemoveObserver(PrefStore::Observer* observer) override;
-  bool HasObservers() const override;
-  bool IsInitializationComplete() const override;
-  bool GetValue(const std::string& key,
-                const base::Value** result) const override;
-
-  // Methods of PersistentPrefStore.
-  bool GetMutableValue(const std::string& key, base::Value** result) override;
-  void SetValue(const std::string& key,
-                scoped_ptr<base::Value> value,
-                uint32_t flags) override;
-  void SetValueSilently(const std::string& key,
-                        scoped_ptr<base::Value> value,
-                        uint32_t flags) override;
-  void RemoveValue(const std::string& key, uint32_t flags) override;
-  bool ReadOnly() const override;
-  PrefReadError GetReadError() const override;
-  PrefReadError ReadPrefs() override;
-  void ReadPrefsAsync(ReadErrorDelegate* delegate) override;
-  void CommitPendingWrite() override;
-  void SchedulePendingLossyWrites() override;
-  void ReportValueChanged(const std::string& key, uint32_t flags) override;
-
-  // Methods of PrefStore::Observer.
-  void OnPrefValueChanged(const std::string& key) override;
-  void OnInitializationCompleted(bool succeeded) override;
-
-  void RegisterOverlayPref(const std::string& key);
-  void RegisterOverlayPref(const std::string& overlay_key,
-                           const std::string& underlay_key);
-
- protected:
-  ~OverlayUserPrefStore() override;
-
- private:
-  typedef std::map<std::string, std::string> NamesMap;
-
-  const std::string& GetOverlayKey(const std::string& underlay_key) const;
-  const std::string& GetUnderlayKey(const std::string& overlay_key) const;
-
-  // Returns true if |key| corresponds to a preference that shall be stored in
-  // an in-memory PrefStore that is not persisted to disk.
-  bool ShallBeStoredInOverlay(const std::string& key) const;
-
-  base::ObserverList<PrefStore::Observer, true> observers_;
-  PrefValueMap overlay_;
-  scoped_refptr<PersistentPrefStore> underlay_;
-  NamesMap overlay_to_underlay_names_map_;
-  NamesMap underlay_to_overlay_names_map_;
-
-  DISALLOW_COPY_AND_ASSIGN(OverlayUserPrefStore);
-};
-
-#endif  // BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/overlay_user_pref_store.h"
diff --git a/base/prefs/persistent_pref_store.h b/base/prefs/persistent_pref_store.h
index 89c7a71..a0fcf685 100644
--- a/base/prefs/persistent_pref_store.h
+++ b/base/prefs/persistent_pref_store.h
@@ -2,76 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PERSISTENT_PREF_STORE_H_
-#define BASE_PREFS_PERSISTENT_PREF_STORE_H_
-
-#include <string>
-
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/writeable_pref_store.h"
-
-// This interface is complementary to the PrefStore interface, declaring
-// additional functionality that adds support for setting values and persisting
-// the data to some backing store.
-class BASE_PREFS_EXPORT PersistentPrefStore : public WriteablePrefStore {
- public:
-  // Unique integer code for each type of error so we can report them
-  // distinctly in a histogram.
-  // NOTE: Don't change the explicit values of the enums as it will change the
-  // server's meaning of the histogram.
-  enum PrefReadError {
-    PREF_READ_ERROR_NONE = 0,
-    PREF_READ_ERROR_JSON_PARSE = 1,
-    PREF_READ_ERROR_JSON_TYPE = 2,
-    PREF_READ_ERROR_ACCESS_DENIED = 3,
-    PREF_READ_ERROR_FILE_OTHER = 4,
-    PREF_READ_ERROR_FILE_LOCKED = 5,
-    PREF_READ_ERROR_NO_FILE = 6,
-    PREF_READ_ERROR_JSON_REPEAT = 7,
-    // PREF_READ_ERROR_OTHER = 8,  // Deprecated.
-    PREF_READ_ERROR_FILE_NOT_SPECIFIED = 9,
-    // Indicates that ReadPrefs() couldn't complete synchronously and is waiting
-    // for an asynchronous task to complete first.
-    PREF_READ_ERROR_ASYNCHRONOUS_TASK_INCOMPLETE = 10,
-    PREF_READ_ERROR_MAX_ENUM
-  };
-
-  class ReadErrorDelegate {
-   public:
-    virtual ~ReadErrorDelegate() {}
-
-    virtual void OnError(PrefReadError error) = 0;
-  };
-
-  // Whether the store is in a pseudo-read-only mode where changes are not
-  // actually persisted to disk.  This happens in some cases when there are
-  // read errors during startup.
-  virtual bool ReadOnly() const = 0;
-
-  // Gets the read error. Only valid if IsInitializationComplete() returns true.
-  virtual PrefReadError GetReadError() const = 0;
-
-  // Reads the preferences from disk. Notifies observers via
-  // "PrefStore::OnInitializationCompleted" when done.
-  virtual PrefReadError ReadPrefs() = 0;
-
-  // Reads the preferences from disk asynchronously. Notifies observers via
-  // "PrefStore::OnInitializationCompleted" when done. Also it fires
-  // |error_delegate| if it is not NULL and reading error has occurred.
-  // Owns |error_delegate|.
-  virtual void ReadPrefsAsync(ReadErrorDelegate* error_delegate) = 0;
-
-  // Lands any pending writes to disk.
-  virtual void CommitPendingWrite() = 0;
-
-  // Schedule a write if there is any lossy data pending. Unlike
-  // CommitPendingWrite() this does not immediately sync to disk, instead it
-  // triggers an eventual write if there is lossy data pending and if there
-  // isn't one scheduled already.
-  virtual void SchedulePendingLossyWrites() = 0;
-
- protected:
-  ~PersistentPrefStore() override {}
-};
-
-#endif  // BASE_PREFS_PERSISTENT_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/persistent_pref_store.h"
diff --git a/base/prefs/pref_change_registrar.h b/base/prefs/pref_change_registrar.h
index cd5a2332..517b63f 100644
--- a/base/prefs/pref_change_registrar.h
+++ b/base/prefs/pref_change_registrar.h
@@ -2,80 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
-#define BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
-
-#include <map>
-#include <string>
-
-#include "base/callback.h"
-#include "base/macros.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_observer.h"
-
-class PrefService;
-
-// Automatically manages the registration of one or more pref change observers
-// with a PrefStore. Functions much like NotificationRegistrar, but specifically
-// manages observers of preference changes. When the Registrar is destroyed,
-// all registered observers are automatically unregistered with the PrefStore.
-class BASE_PREFS_EXPORT PrefChangeRegistrar : public PrefObserver {
- public:
-  // You can register this type of callback if you need to know the
-  // path of the preference that is changing.
-  typedef base::Callback<void(const std::string&)> NamedChangeCallback;
-
-  PrefChangeRegistrar();
-  virtual ~PrefChangeRegistrar();
-
-  // Must be called before adding or removing observers. Can be called more
-  // than once as long as the value of |service| doesn't change.
-  void Init(PrefService* service);
-
-  // Adds a pref observer for the specified pref |path| and |obs| observer
-  // object. All registered observers will be automatically unregistered
-  // when the registrar's destructor is called.
-  //
-  // The second version binds a callback that will receive the path of
-  // the preference that is changing as its parameter.
-  //
-  // Only one observer may be registered per path.
-  void Add(const std::string& path, const base::Closure& obs);
-  void Add(const std::string& path, const NamedChangeCallback& obs);
-
-  // Removes the pref observer registered for |path|.
-  void Remove(const std::string& path);
-
-  // Removes all observers that have been previously added with a call to Add.
-  void RemoveAll();
-
-  // Returns true if no pref observers are registered.
-  bool IsEmpty() const;
-
-  // Check whether |pref| is in the set of preferences being observed.
-  bool IsObserved(const std::string& pref);
-
-  // Check whether any of the observed preferences has the managed bit set.
-  bool IsManaged();
-
-  // Return the PrefService for this registrar.
-  PrefService* prefs();
-  const PrefService* prefs() const;
-
- private:
-  // PrefObserver:
-  void OnPreferenceChanged(PrefService* service,
-                           const std::string& pref_name) override;
-
-  static void InvokeUnnamedCallback(const base::Closure& callback,
-                                    const std::string& pref_name);
-
-  typedef std::map<std::string, NamedChangeCallback> ObserverMap;
-
-  ObserverMap observers_;
-  PrefService* service_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefChangeRegistrar);
-};
-
-#endif  // BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_change_registrar.h"
diff --git a/base/prefs/pref_filter.h b/base/prefs/pref_filter.h
index 82a44c6..6ed06bc 100644
--- a/base/prefs/pref_filter.h
+++ b/base/prefs/pref_filter.h
@@ -2,54 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_FILTER_H_
-#define BASE_PREFS_PREF_FILTER_H_
-
-#include <string>
-
-#include "base/callback_forward.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/prefs/base_prefs_export.h"
-
-namespace base {
-class DictionaryValue;
-class Value;
-}  // namespace base
-
-// Filters preferences as they are loaded from disk or updated at runtime.
-// Currently supported only by JsonPrefStore.
-class BASE_PREFS_EXPORT PrefFilter {
- public:
-  // A callback to be invoked when |prefs| have been read (and possibly
-  // pre-modified) and are now ready to be handed back to this callback's
-  // builder. |schedule_write| indicates whether a write should be immediately
-  // scheduled (typically because the |prefs| were pre-modified).
-  typedef base::Callback<void(scoped_ptr<base::DictionaryValue> prefs,
-                              bool schedule_write)> PostFilterOnLoadCallback;
-
-  virtual ~PrefFilter() {}
-
-  // This method is given ownership of the |pref_store_contents| read from disk
-  // before the underlying PersistentPrefStore gets to use them. It must hand
-  // them back via |post_filter_on_load_callback|, but may modify them first.
-  // Note: This method is asynchronous, which may make calls like
-  // PersistentPrefStore::ReadPrefs() asynchronous. The owner of filtered
-  // PersistentPrefStores should handle this to make the reads look synchronous
-  // to external users (see SegregatedPrefStore::ReadPrefs() for an example).
-  virtual void FilterOnLoad(
-      const PostFilterOnLoadCallback& post_filter_on_load_callback,
-      scoped_ptr<base::DictionaryValue> pref_store_contents) = 0;
-
-  // Receives notification when a pref store value is changed, before Observers
-  // are notified.
-  virtual void FilterUpdate(const std::string& path) = 0;
-
-  // Receives notification when the pref store is about to serialize data
-  // contained in |pref_store_contents| to a string. Modifications to
-  // |pref_store_contents| will be persisted to disk and also affect the
-  // in-memory state.
-  virtual void FilterSerializeData(
-      base::DictionaryValue* pref_store_contents) = 0;
-};
-
-#endif  // BASE_PREFS_PREF_FILTER_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_filter.h"
diff --git a/base/prefs/pref_member.h b/base/prefs/pref_member.h
index 4290c0db..ff90e5eb 100644
--- a/base/prefs/pref_member.h
+++ b/base/prefs/pref_member.h
@@ -1,355 +1,7 @@
 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
-//
-// A helper class that stays in sync with a preference (bool, int, real,
-// string or filepath).  For example:
-//
-// class MyClass {
-//  public:
-//   MyClass(PrefService* prefs) {
-//     my_string_.Init(prefs::kHomePage, prefs);
-//   }
-//  private:
-//   StringPrefMember my_string_;
-// };
-//
-// my_string_ should stay in sync with the prefs::kHomePage pref and will
-// update if either the pref changes or if my_string_.SetValue is called.
-//
-// An optional observer can be passed into the Init method which can be used to
-// notify MyClass of changes. Note that if you use SetValue(), the observer
-// will not be notified.
 
-#ifndef BASE_PREFS_PREF_MEMBER_H_
-#define BASE_PREFS_PREF_MEMBER_H_
-
-#include <string>
-#include <vector>
-
-#include "base/bind.h"
-#include "base/callback_forward.h"
-#include "base/files/file_path.h"
-#include "base/logging.h"
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_observer.h"
-#include "base/single_thread_task_runner.h"
-#include "base/values.h"
-
-class PrefService;
-
-namespace subtle {
-
-class BASE_PREFS_EXPORT PrefMemberBase : public PrefObserver {
- public:
-  // Type of callback you can register if you need to know the name of
-  // the pref that is changing.
-  typedef base::Callback<void(const std::string&)> NamedChangeCallback;
-
-  PrefService* prefs() { return prefs_; }
-  const PrefService* prefs() const { return prefs_; }
-
- protected:
-  class BASE_PREFS_EXPORT Internal
-      : public base::RefCountedThreadSafe<Internal> {
-   public:
-    Internal();
-
-    // Update the value, either by calling |UpdateValueInternal| directly
-    // or by dispatching to the right thread.
-    // Takes ownership of |value|.
-    void UpdateValue(base::Value* value,
-                     bool is_managed,
-                     bool is_user_modifiable,
-                     const base::Closure& callback) const;
-
-    void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner);
-
-    // See PrefMember<> for description.
-    bool IsManaged() const {
-      return is_managed_;
-    }
-
-    bool IsUserModifiable() const {
-      return is_user_modifiable_;
-    }
-
-   protected:
-    friend class base::RefCountedThreadSafe<Internal>;
-    virtual ~Internal();
-
-    void CheckOnCorrectThread() const {
-      DCHECK(IsOnCorrectThread());
-    }
-
-   private:
-    // This method actually updates the value. It should only be called from
-    // the thread the PrefMember is on.
-    virtual bool UpdateValueInternal(const base::Value& value) const = 0;
-
-    bool IsOnCorrectThread() const;
-
-    scoped_refptr<base::SingleThreadTaskRunner> thread_task_runner_;
-    mutable bool is_managed_;
-    mutable bool is_user_modifiable_;
-
-    DISALLOW_COPY_AND_ASSIGN(Internal);
-  };
-
-  PrefMemberBase();
-  virtual ~PrefMemberBase();
-
-  // See PrefMember<> for description.
-  void Init(const std::string& pref_name,
-            PrefService* prefs,
-            const NamedChangeCallback& observer);
-  void Init(const std::string& pref_name, PrefService* prefs);
-
-  virtual void CreateInternal() const = 0;
-
-  // See PrefMember<> for description.
-  void Destroy();
-
-  void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner);
-
-  // PrefObserver
-  void OnPreferenceChanged(PrefService* service,
-                           const std::string& pref_name) override;
-
-  void VerifyValuePrefName() const {
-    DCHECK(!pref_name_.empty());
-  }
-
-  // This method is used to do the actual sync with the preference.
-  // Note: it is logically const, because it doesn't modify the state
-  // seen by the outside world. It is just doing a lazy load behind the scenes.
-  void UpdateValueFromPref(const base::Closure& callback) const;
-
-  // Verifies the preference name, and lazily loads the preference value if
-  // it hasn't been loaded yet.
-  void VerifyPref() const;
-
-  const std::string& pref_name() const { return pref_name_; }
-
-  virtual Internal* internal() const = 0;
-
-  // Used to allow registering plain base::Closure callbacks.
-  static void InvokeUnnamedCallback(const base::Closure& callback,
-                                    const std::string& pref_name);
-
- private:
-  // Ordered the members to compact the class instance.
-  std::string pref_name_;
-  NamedChangeCallback observer_;
-  PrefService* prefs_;
-
- protected:
-  bool setting_value_;
-};
-
-// This function implements StringListPrefMember::UpdateValue().
-// It is exposed here for testing purposes.
-bool BASE_PREFS_EXPORT PrefMemberVectorStringUpdate(
-    const base::Value& value,
-    std::vector<std::string>* string_vector);
-
-}  // namespace subtle
-
-template <typename ValueType>
-class PrefMember : public subtle::PrefMemberBase {
- public:
-  // Defer initialization to an Init method so it's easy to make this class be
-  // a member variable.
-  PrefMember() {}
-  virtual ~PrefMember() {}
-
-  // Do the actual initialization of the class.  Use the two-parameter
-  // version if you don't want any notifications of changes.  This
-  // method should only be called on the UI thread.
-  void Init(const std::string& pref_name,
-            PrefService* prefs,
-            const NamedChangeCallback& observer) {
-    subtle::PrefMemberBase::Init(pref_name, prefs, observer);
-  }
-  void Init(const std::string& pref_name,
-            PrefService* prefs,
-            const base::Closure& observer) {
-    subtle::PrefMemberBase::Init(
-        pref_name, prefs,
-        base::Bind(&PrefMemberBase::InvokeUnnamedCallback, observer));
-  }
-  void Init(const std::string& pref_name, PrefService* prefs) {
-    subtle::PrefMemberBase::Init(pref_name, prefs);
-  }
-
-  // Unsubscribes the PrefMember from the PrefService. After calling this
-  // function, the PrefMember may not be used any more on the UI thread.
-  // Assuming |MoveToThread| was previously called, |GetValue|, |IsManaged|,
-  // and |IsUserModifiable| can still be called from the other thread but
-  // the results will no longer update from the PrefService.
-  // This method should only be called on the UI thread.
-  void Destroy() {
-    subtle::PrefMemberBase::Destroy();
-  }
-
-  // Moves the PrefMember to another thread, allowing read accesses from there.
-  // Changes from the PrefService will be propagated asynchronously
-  // via PostTask.
-  // This method should only be used from the thread the PrefMember is currently
-  // on, which is the UI thread by default.
-  void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner) {
-    subtle::PrefMemberBase::MoveToThread(task_runner);
-  }
-
-  // Check whether the pref is managed, i.e. controlled externally through
-  // enterprise configuration management (e.g. windows group policy). Returns
-  // false for unknown prefs.
-  // This method should only be used from the thread the PrefMember is currently
-  // on, which is the UI thread unless changed by |MoveToThread|.
-  bool IsManaged() const {
-    VerifyPref();
-    return internal_->IsManaged();
-  }
-
-  // Checks whether the pref can be modified by the user. This returns false
-  // when the pref is managed by a policy or an extension, and when a command
-  // line flag overrides the pref.
-  // This method should only be used from the thread the PrefMember is currently
-  // on, which is the UI thread unless changed by |MoveToThread|.
-  bool IsUserModifiable() const {
-    VerifyPref();
-    return internal_->IsUserModifiable();
-  }
-
-  // Retrieve the value of the member variable.
-  // This method should only be used from the thread the PrefMember is currently
-  // on, which is the UI thread unless changed by |MoveToThread|.
-  ValueType GetValue() const {
-    VerifyPref();
-    return internal_->value();
-  }
-
-  // Provided as a convenience.
-  ValueType operator*() const {
-    return GetValue();
-  }
-
-  // Set the value of the member variable.
-  // This method should only be called on the UI thread.
-  void SetValue(const ValueType& value) {
-    VerifyValuePrefName();
-    setting_value_ = true;
-    UpdatePref(value);
-    setting_value_ = false;
-  }
-
-  // Returns the pref name.
-  const std::string& GetPrefName() const {
-    return pref_name();
-  }
-
- private:
-  class Internal : public subtle::PrefMemberBase::Internal {
-   public:
-    Internal() : value_(ValueType()) {}
-
-    ValueType value() {
-      CheckOnCorrectThread();
-      return value_;
-    }
-
-   protected:
-    ~Internal() override {}
-
-    BASE_PREFS_EXPORT bool UpdateValueInternal(
-        const base::Value& value) const override;
-
-    // We cache the value of the pref so we don't have to keep walking the pref
-    // tree.
-    mutable ValueType value_;
-
-   private:
-    DISALLOW_COPY_AND_ASSIGN(Internal);
-  };
-
-  Internal* internal() const override { return internal_.get(); }
-  void CreateInternal() const override { internal_ = new Internal(); }
-
-  // This method is used to do the actual sync with pref of the specified type.
-  void BASE_PREFS_EXPORT UpdatePref(const ValueType& value);
-
-  mutable scoped_refptr<Internal> internal_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefMember);
-};
-
-// Declaration of template specialization need to be repeated here
-// specifically for each specialization (rather than just once above)
-// or at least one of our compilers won't be happy in all cases.
-// Specifically, it was failing on ChromeOS with a complaint about
-// PrefMember<FilePath>::UpdateValueInternal not being defined when
-// built in a chroot with the following parameters:
-//
-// FEATURES="noclean nostrip" USE="-chrome_debug -chrome_remoting
-// -chrome_internal -chrome_pdf component_build"
-// ~/trunk/goma/goma-wrapper cros_chrome_make --board=${BOARD}
-// --install --runhooks
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<bool>::UpdatePref(const bool& value);
-
-template <>
-BASE_PREFS_EXPORT bool PrefMember<bool>::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<int>::UpdatePref(const int& value);
-
-template <>
-BASE_PREFS_EXPORT bool PrefMember<int>::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<double>::UpdatePref(const double& value);
-
-template <>
-BASE_PREFS_EXPORT bool PrefMember<double>::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<std::string>::UpdatePref(
-    const std::string& value);
-
-template <>
-BASE_PREFS_EXPORT bool PrefMember<std::string>::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<base::FilePath>::UpdatePref(
-    const base::FilePath& value);
-
-template <>
-BASE_PREFS_EXPORT bool
-PrefMember<base::FilePath>::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-template <>
-BASE_PREFS_EXPORT void PrefMember<std::vector<std::string> >::UpdatePref(
-    const std::vector<std::string>& value);
-
-template <>
-BASE_PREFS_EXPORT bool
-PrefMember<std::vector<std::string> >::Internal::UpdateValueInternal(
-    const base::Value& value) const;
-
-typedef PrefMember<bool> BooleanPrefMember;
-typedef PrefMember<int> IntegerPrefMember;
-typedef PrefMember<double> DoublePrefMember;
-typedef PrefMember<std::string> StringPrefMember;
-typedef PrefMember<base::FilePath> FilePathPrefMember;
-// This preference member is expensive for large string arrays.
-typedef PrefMember<std::vector<std::string> > StringListPrefMember;
-
-#endif  // BASE_PREFS_PREF_MEMBER_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_member.h"
diff --git a/base/prefs/pref_notifier.h b/base/prefs/pref_notifier.h
index e0df260c..d99f5b8 100644
--- a/base/prefs/pref_notifier.h
+++ b/base/prefs/pref_notifier.h
@@ -2,25 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_NOTIFIER_H_
-#define BASE_PREFS_PREF_NOTIFIER_H_
-
-#include <string>
-
-// Delegate interface used by PrefValueStore to notify its owner about changes
-// to the preference values.
-// TODO(mnissler, danno): Move this declaration to pref_value_store.h once we've
-// cleaned up all public uses of this interface.
-class PrefNotifier {
- public:
-  virtual ~PrefNotifier() {}
-
-  // Sends out a change notification for the preference identified by
-  // |pref_name|.
-  virtual void OnPreferenceChanged(const std::string& pref_name) = 0;
-
-  // Broadcasts the intialization completed notification.
-  virtual void OnInitializationCompleted(bool succeeded) = 0;
-};
-
-#endif  // BASE_PREFS_PREF_NOTIFIER_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_notifier.h"
diff --git a/base/prefs/pref_notifier_impl.h b/base/prefs/pref_notifier_impl.h
index 6e62e232..f47cc3e5 100644
--- a/base/prefs/pref_notifier_impl.h
+++ b/base/prefs/pref_notifier_impl.h
@@ -2,73 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_NOTIFIER_IMPL_H_
-#define BASE_PREFS_PREF_NOTIFIER_IMPL_H_
-
-#include <list>
-#include <string>
-
-#include "base/callback.h"
-#include "base/compiler_specific.h"
-#include "base/containers/hash_tables.h"
-#include "base/macros.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_notifier.h"
-#include "base/prefs/pref_observer.h"
-#include "base/threading/thread_checker.h"
-
-class PrefService;
-
-// The PrefNotifier implementation used by the PrefService.
-class BASE_PREFS_EXPORT PrefNotifierImpl
-    : public NON_EXPORTED_BASE(PrefNotifier) {
- public:
-  PrefNotifierImpl();
-  explicit PrefNotifierImpl(PrefService* pref_service);
-  ~PrefNotifierImpl() override;
-
-  // If the pref at the given path changes, we call the observer's
-  // OnPreferenceChanged method.
-  void AddPrefObserver(const std::string& path, PrefObserver* observer);
-  void RemovePrefObserver(const std::string& path, PrefObserver* observer);
-
-  // We run the callback once, when initialization completes. The bool
-  // parameter will be set to true for successful initialization,
-  // false for unsuccessful.
-  void AddInitObserver(base::Callback<void(bool)> observer);
-
-  void SetPrefService(PrefService* pref_service);
-
- protected:
-  // PrefNotifier overrides.
-  void OnPreferenceChanged(const std::string& pref_name) override;
-  void OnInitializationCompleted(bool succeeded) override;
-
-  // A map from pref names to a list of observers. Observers get fired in the
-  // order they are added. These should only be accessed externally for unit
-  // testing.
-  typedef base::ObserverList<PrefObserver> PrefObserverList;
-  typedef base::hash_map<std::string, PrefObserverList*> PrefObserverMap;
-
-  typedef std::list<base::Callback<void(bool)>> PrefInitObserverList;
-
-  const PrefObserverMap* pref_observers() const { return &pref_observers_; }
-
- private:
-  // For the given pref_name, fire any observer of the pref. Virtual so it can
-  // be mocked for unit testing.
-  virtual void FireObservers(const std::string& path);
-
-  // Weak reference; the notifier is owned by the PrefService.
-  PrefService* pref_service_;
-
-  PrefObserverMap pref_observers_;
-  PrefInitObserverList init_observers_;
-
-  base::ThreadChecker thread_checker_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefNotifierImpl);
-};
-
-#endif  // BASE_PREFS_PREF_NOTIFIER_IMPL_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_notifier_impl.h"
diff --git a/base/prefs/pref_observer.h b/base/prefs/pref_observer.h
index 5d8f5b63..df5d1af 100644
--- a/base/prefs/pref_observer.h
+++ b/base/prefs/pref_observer.h
@@ -2,20 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_OBSERVER_H_
-#define BASE_PREFS_PREF_OBSERVER_H_
-
-#include <string>
-
-class PrefService;
-
-// Used internally to the Prefs subsystem to pass preference change
-// notifications between PrefService, PrefNotifierImpl and
-// PrefChangeRegistrar.
-class PrefObserver {
- public:
-  virtual void OnPreferenceChanged(PrefService* service,
-                                   const std::string& pref_name) = 0;
-};
-
-#endif  // BASE_PREFS_PREF_OBSERVER_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_observer.h"
diff --git a/base/prefs/pref_registry.h b/base/prefs/pref_registry.h
index 7e141d8..94126d1 100644
--- a/base/prefs/pref_registry.h
+++ b/base/prefs/pref_registry.h
@@ -2,88 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_REGISTRY_H_
-#define BASE_PREFS_PREF_REGISTRY_H_
-
-#include <stdint.h>
-
-#include "base/containers/hash_tables.h"
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_value_map.h"
-
-namespace base {
-class Value;
-}
-
-class DefaultPrefStore;
-class PrefStore;
-
-// Preferences need to be registered with a type and default value
-// before they are used.
-//
-// The way you use a PrefRegistry is that you register all required
-// preferences on it (via one of its subclasses), then pass it as a
-// construction parameter to PrefService.
-//
-// Currently, registrations after constructing the PrefService will
-// also work, but this is being deprecated.
-class BASE_PREFS_EXPORT PrefRegistry : public base::RefCounted<PrefRegistry> {
- public:
-  // Registration flags that can be specified which impact how the pref will
-  // behave or be stored. This will be passed in a bitmask when the pref is
-  // registered. Subclasses of PrefRegistry can specify their own flags. Care
-  // must be taken to ensure none of these overlap with the flags below.
-  enum PrefRegistrationFlags : uint32_t {
-    // No flags are specified.
-    NO_REGISTRATION_FLAGS = 0,
-
-    // The first 8 bits are reserved for subclasses of PrefRegistry to use.
-
-    // This marks the pref as "lossy". There is no strict time guarantee on when
-    // a lossy pref will be persisted to permanent storage when it is modified.
-    LOSSY_PREF = 1 << 8,
-  };
-
-  typedef PrefValueMap::const_iterator const_iterator;
-  typedef base::hash_map<std::string, uint32_t> PrefRegistrationFlagsMap;
-
-  PrefRegistry();
-
-  // Retrieve the set of registration flags for the given preference. The return
-  // value is a bitmask of PrefRegistrationFlags.
-  uint32_t GetRegistrationFlags(const std::string& pref_name) const;
-
-  // Gets the registered defaults.
-  scoped_refptr<PrefStore> defaults();
-
-  // Allows iteration over defaults.
-  const_iterator begin() const;
-  const_iterator end() const;
-
-  // Changes the default value for a preference. Takes ownership of |value|.
-  //
-  // |pref_name| must be a previously registered preference.
-  void SetDefaultPrefValue(const std::string& pref_name, base::Value* value);
-
- protected:
-  friend class base::RefCounted<PrefRegistry>;
-  virtual ~PrefRegistry();
-
-  // Used by subclasses to register a default value and registration flags for
-  // a preference. |flags| is a bitmask of |PrefRegistrationFlags|.
-  void RegisterPreference(const std::string& path,
-                          base::Value* default_value,
-                          uint32_t flags);
-
-  scoped_refptr<DefaultPrefStore> defaults_;
-
-  // A map of pref name to a bitmask of PrefRegistrationFlags.
-  PrefRegistrationFlagsMap registration_flags_;
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(PrefRegistry);
-};
-
-#endif  // BASE_PREFS_PREF_REGISTRY_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_registry.h"
diff --git a/base/prefs/pref_registry_simple.h b/base/prefs/pref_registry_simple.h
index 6afc012b..0f157a2a 100644
--- a/base/prefs/pref_registry_simple.h
+++ b/base/prefs/pref_registry_simple.h
@@ -2,90 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
-#define BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
-
-#include <stdint.h>
-
-#include <string>
-
-#include "base/macros.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_registry.h"
-
-namespace base {
-class DictionaryValue;
-class FilePath;
-class ListValue;
-}
-
-// A simple implementation of PrefRegistry.
-class BASE_PREFS_EXPORT PrefRegistrySimple : public PrefRegistry {
- public:
-  PrefRegistrySimple();
-
-  void RegisterBooleanPref(const std::string& path, bool default_value);
-  void RegisterIntegerPref(const std::string& path, int default_value);
-  void RegisterDoublePref(const std::string& path, double default_value);
-  void RegisterStringPref(const std::string& path,
-                          const std::string& default_value);
-  void RegisterFilePathPref(const std::string& path,
-                            const base::FilePath& default_value);
-  void RegisterListPref(const std::string& path);
-  void RegisterDictionaryPref(const std::string& path);
-  void RegisterListPref(const std::string& path,
-                        base::ListValue* default_value);
-  void RegisterDictionaryPref(const std::string& path,
-                              base::DictionaryValue* default_value);
-  void RegisterInt64Pref(const std::string& path, int64_t default_value);
-  void RegisterUint64Pref(const std::string&, uint64_t default_value);
-
-  // Versions of registration functions that accept PrefRegistrationFlags.
-  // |flags| is a bitmask of PrefRegistrationFlags.
-  void RegisterBooleanPref(const std::string&,
-                           bool default_value,
-                           uint32_t flags);
-  void RegisterIntegerPref(const std::string&,
-                           int default_value,
-                           uint32_t flags);
-  void RegisterDoublePref(const std::string&,
-                          double default_value,
-                          uint32_t flags);
-  void RegisterStringPref(const std::string&,
-                          const std::string& default_value,
-                          uint32_t flags);
-  void RegisterFilePathPref(const std::string&,
-                            const base::FilePath& default_value,
-                            uint32_t flags);
-  void RegisterListPref(const std::string&, uint32_t flags);
-  void RegisterDictionaryPref(const std::string&, uint32_t flags);
-  void RegisterListPref(const std::string&,
-                        base::ListValue* default_value,
-                        uint32_t flags);
-  void RegisterDictionaryPref(const std::string&,
-                              base::DictionaryValue* default_value,
-                              uint32_t flags);
-  void RegisterInt64Pref(const std::string&,
-                         int64_t default_value,
-                         uint32_t flags);
-  void RegisterUint64Pref(const std::string&,
-                          uint64_t default_value,
-                          uint32_t flags);
-
- protected:
-  ~PrefRegistrySimple() override;
-
-  // Allows subclasses to hook into pref registration.
-  virtual void OnPrefRegistered(const std::string&,
-                                base::Value* default_value,
-                                uint32_t flags);
-
- private:
-  void RegisterPrefAndNotify(const std::string&,
-                             base::Value* default_value,
-                             uint32_t flags);
-
-  DISALLOW_COPY_AND_ASSIGN(PrefRegistrySimple);
-};
-
-#endif  // BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_registry_simple.h"
diff --git a/base/prefs/pref_service.h b/base/prefs/pref_service.h
index bec7830..aced2f0 100644
--- a/base/prefs/pref_service.h
+++ b/base/prefs/pref_service.h
@@ -2,384 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-// This provides a way to access the application's current preferences.
-
-// Chromium settings and storage represent user-selected preferences and
-// information and MUST not be extracted, overwritten or modified except
-// through Chromium defined APIs.
-
-#ifndef BASE_PREFS_PREF_SERVICE_H_
-#define BASE_PREFS_PREF_SERVICE_H_
-
-#include <stdint.h>
-
-#include <set>
-#include <string>
-
-#include "base/callback.h"
-#include "base/compiler_specific.h"
-#include "base/containers/hash_tables.h"
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/persistent_pref_store.h"
-#include "base/threading/non_thread_safe.h"
-#include "base/values.h"
-
-class PrefNotifier;
-class PrefNotifierImpl;
-class PrefObserver;
-class PrefRegistry;
-class PrefValueStore;
-class PrefStore;
-
-namespace base {
-class FilePath;
-}
-
-namespace subtle {
-class PrefMemberBase;
-class ScopedUserPrefUpdateBase;
-}
-
-// Base class for PrefServices. You can use the base class to read and
-// interact with preferences, but not to register new preferences; for
-// that see e.g. PrefRegistrySimple.
-//
-// Settings and storage accessed through this class represent
-// user-selected preferences and information and MUST not be
-// extracted, overwritten or modified except through the defined APIs.
-class BASE_PREFS_EXPORT PrefService : public base::NonThreadSafe {
- public:
-  enum PrefInitializationStatus {
-    INITIALIZATION_STATUS_WAITING,
-    INITIALIZATION_STATUS_SUCCESS,
-    INITIALIZATION_STATUS_CREATED_NEW_PREF_STORE,
-    INITIALIZATION_STATUS_ERROR
-  };
-
-  // A helper class to store all the information associated with a preference.
-  class BASE_PREFS_EXPORT Preference {
-   public:
-    // The type of the preference is determined by the type with which it is
-    // registered. This type needs to be a boolean, integer, double, string,
-    // dictionary (a branch), or list.  You shouldn't need to construct this on
-    // your own; use the PrefService::Register*Pref methods instead.
-    Preference(const PrefService* service,
-               const std::string& name,
-               base::Value::Type type);
-    ~Preference() {}
-
-    // Returns the name of the Preference (i.e., the key, e.g.,
-    // browser.window_placement).
-    const std::string name() const;
-
-    // Returns the registered type of the preference.
-    base::Value::Type GetType() const;
-
-    // Returns the value of the Preference, falling back to the registered
-    // default value if no other has been set.
-    const base::Value* GetValue() const;
-
-    // Returns the value recommended by the admin, if any.
-    const base::Value* GetRecommendedValue() const;
-
-    // Returns true if the Preference is managed, i.e. set by an admin policy.
-    // Since managed prefs have the highest priority, this also indicates
-    // whether the pref is actually being controlled by the policy setting.
-    bool IsManaged() const;
-
-    // Returns true if the Preference is controlled by the custodian of the
-    // supervised user. Since a supervised user is not expected to have an admin
-    // policy, this is the controlling pref if set.
-    bool IsManagedByCustodian() const;
-
-    // Returns true if the Preference is recommended, i.e. set by an admin
-    // policy but the user is allowed to change it.
-    bool IsRecommended() const;
-
-    // Returns true if the Preference has a value set by an extension, even if
-    // that value is being overridden by a higher-priority source.
-    bool HasExtensionSetting() const;
-
-    // Returns true if the Preference has a user setting, even if that value is
-    // being overridden by a higher-priority source.
-    bool HasUserSetting() const;
-
-    // Returns true if the Preference value is currently being controlled by an
-    // extension, and not by any higher-priority source.
-    bool IsExtensionControlled() const;
-
-    // Returns true if the Preference value is currently being controlled by a
-    // user setting, and not by any higher-priority source.
-    bool IsUserControlled() const;
-
-    // Returns true if the Preference is currently using its default value,
-    // and has not been set by any higher-priority source (even with the same
-    // value).
-    bool IsDefaultValue() const;
-
-    // Returns true if the user can change the Preference value, which is the
-    // case if no higher-priority source than the user store controls the
-    // Preference.
-    bool IsUserModifiable() const;
-
-    // Returns true if an extension can change the Preference value, which is
-    // the case if no higher-priority source than the extension store controls
-    // the Preference.
-    bool IsExtensionModifiable() const;
-
-    // Return the registration flags for this pref as a bitmask of
-    // PrefRegistry::PrefRegistrationFlags.
-    uint32_t registration_flags() const { return registration_flags_; }
-
-   private:
-    friend class PrefService;
-
-    PrefValueStore* pref_value_store() const {
-      return pref_service_->pref_value_store_.get();
-    }
-
-    const std::string name_;
-
-    const base::Value::Type type_;
-
-    uint32_t registration_flags_;
-
-    // Reference to the PrefService in which this pref was created.
-    const PrefService* pref_service_;
-  };
-
-  // You may wish to use PrefServiceFactory or one of its subclasses
-  // for simplified construction.
-  PrefService(
-      PrefNotifierImpl* pref_notifier,
-      PrefValueStore* pref_value_store,
-      PersistentPrefStore* user_prefs,
-      PrefRegistry* pref_registry,
-      base::Callback<void(PersistentPrefStore::PrefReadError)>
-          read_error_callback,
-      bool async);
-  virtual ~PrefService();
-
-  // Lands pending writes to disk. This should only be used if we need to save
-  // immediately (basically, during shutdown).
-  void CommitPendingWrite();
-
-  // Schedule a write if there is any lossy data pending. Unlike
-  // CommitPendingWrite() this does not immediately sync to disk, instead it
-  // triggers an eventual write if there is lossy data pending and if there
-  // isn't one scheduled already.
-  void SchedulePendingLossyWrites();
-
-  // Returns true if the preference for the given preference name is available
-  // and is managed.
-  bool IsManagedPreference(const std::string& pref_name) const;
-
-  // Returns true if the preference for the given preference name is available
-  // and is controlled by the parent/guardian of the child Account.
-  bool IsPreferenceManagedByCustodian(const std::string& pref_name) const;
-
-  // Returns |true| if a preference with the given name is available and its
-  // value can be changed by the user.
-  bool IsUserModifiablePreference(const std::string& pref_name) const;
-
-  // Look up a preference.  Returns NULL if the preference is not
-  // registered.
-  const PrefService::Preference* FindPreference(const std::string& path) const;
-
-  // If the path is valid and the value at the end of the path matches the type
-  // specified, it will return the specified value.  Otherwise, the default
-  // value (set when the pref was registered) will be returned.
-  bool GetBoolean(const std::string& path) const;
-  int GetInteger(const std::string& path) const;
-  double GetDouble(const std::string& path) const;
-  std::string GetString(const std::string& path) const;
-  base::FilePath GetFilePath(const std::string& path) const;
-
-  // Returns the branch if it exists, or the registered default value otherwise.
-  // Note that |path| must point to a registered preference. In that case, these
-  // functions will never return NULL.
-  const base::DictionaryValue* GetDictionary(const std::string& path) const;
-  const base::ListValue* GetList(const std::string& path) const;
-
-  // Removes a user pref and restores the pref to its default value.
-  void ClearPref(const std::string& path);
-
-  // If the path is valid (i.e., registered), update the pref value in the user
-  // prefs.
-  // To set the value of dictionary or list values in the pref tree use
-  // Set(), but to modify the value of a dictionary or list use either
-  // ListPrefUpdate or DictionaryPrefUpdate from scoped_user_pref_update.h.
-  void Set(const std::string& path, const base::Value& value);
-  void SetBoolean(const std::string& path, bool value);
-  void SetInteger(const std::string& path, int value);
-  void SetDouble(const std::string& path, double value);
-  void SetString(const std::string& path, const std::string& value);
-  void SetFilePath(const std::string& path, const base::FilePath& value);
-
-  // Int64 helper methods that actually store the given value as a string.
-  // Note that if obtaining the named value via GetDictionary or GetList, the
-  // Value type will be TYPE_STRING.
-  void SetInt64(const std::string& path, int64_t value);
-  int64_t GetInt64(const std::string& path) const;
-
-  // As above, but for unsigned values.
-  void SetUint64(const std::string& path, uint64_t value);
-  uint64_t GetUint64(const std::string& path) const;
-
-  // Returns the value of the given preference, from the user pref store. If
-  // the preference is not set in the user pref store, returns NULL.
-  const base::Value* GetUserPrefValue(const std::string& path) const;
-
-  // Changes the default value for a preference. Takes ownership of |value|.
-  //
-  // Will cause a pref change notification to be fired if this causes
-  // the effective value to change.
-  void SetDefaultPrefValue(const std::string& path, base::Value* value);
-
-  // Returns the default value of the given preference. |path| must point to a
-  // registered preference. In that case, will never return NULL.
-  const base::Value* GetDefaultPrefValue(const std::string& path) const;
-
-  // Returns true if a value has been set for the specified path.
-  // NOTE: this is NOT the same as FindPreference. In particular
-  // FindPreference returns whether RegisterXXX has been invoked, where as
-  // this checks if a value exists for the path.
-  bool HasPrefPath(const std::string& path) const;
-
-  // Returns a dictionary with effective preference values.
-  scoped_ptr<base::DictionaryValue> GetPreferenceValues() const;
-
-  // Returns a dictionary with effective preference values, omitting prefs that
-  // are at their default values.
-  scoped_ptr<base::DictionaryValue> GetPreferenceValuesOmitDefaults() const;
-
-  // Returns a dictionary with effective preference values. Contrary to
-  // GetPreferenceValues(), the paths of registered preferences are not split on
-  // '.' characters. If a registered preference stores a dictionary, however,
-  // the hierarchical structure inside the preference will be preserved.
-  // For example, if "foo.bar" is a registered preference, the result could look
-  // like this:
-  //   {"foo.bar": {"a": {"b": true}}}.
-  scoped_ptr<base::DictionaryValue> GetPreferenceValuesWithoutPathExpansion()
-      const;
-
-  bool ReadOnly() const;
-
-  PrefInitializationStatus GetInitializationStatus() const;
-
-  // Tell our PrefValueStore to update itself to |command_line_store|.
-  // Takes ownership of the store.
-  virtual void UpdateCommandLinePrefStore(PrefStore* command_line_store);
-
-  // We run the callback once, when initialization completes. The bool
-  // parameter will be set to true for successful initialization,
-  // false for unsuccessful.
-  void AddPrefInitObserver(base::Callback<void(bool)> callback);
-
-  // Returns the PrefRegistry object for this service. You should not
-  // use this; the intent is for no registrations to take place after
-  // PrefService has been constructed.
-  //
-  // Instead of using this method, the recommended approach is to
-  // register all preferences for a class Xyz up front in a static
-  // Xyz::RegisterPrefs function, which gets invoked early in the
-  // application's start-up, before a PrefService is created.
-  //
-  // As an example, prefs registration in Chrome is triggered by the
-  // functions chrome::RegisterPrefs (for global preferences) and
-  // chrome::RegisterProfilePrefs (for user-specific preferences)
-  // implemented in chrome/browser/prefs/browser_prefs.cc.
-  PrefRegistry* DeprecatedGetPrefRegistry();
-
- protected:
-  // The PrefNotifier handles registering and notifying preference observers.
-  // It is created and owned by this PrefService. Subclasses may access it for
-  // unit testing.
-  scoped_ptr<PrefNotifierImpl> pref_notifier_;
-
-  // The PrefValueStore provides prioritized preference values. It is owned by
-  // this PrefService. Subclasses may access it for unit testing.
-  scoped_ptr<PrefValueStore> pref_value_store_;
-
-  scoped_refptr<PrefRegistry> pref_registry_;
-
-  // Pref Stores and profile that we passed to the PrefValueStore.
-  scoped_refptr<PersistentPrefStore> user_pref_store_;
-
-  // Callback to call when a read error occurs.
-  base::Callback<void(PersistentPrefStore::PrefReadError)> read_error_callback_;
-
- private:
-  // Hash map expected to be fastest here since it minimises expensive
-  // string comparisons. Order is unimportant, and deletions are rare.
-  // Confirmed on Android where this speeded Chrome startup by roughly 50ms
-  // vs. std::map, and by roughly 180ms vs. std::set of Preference pointers.
-  typedef base::hash_map<std::string, Preference> PreferenceMap;
-
-  // Give access to ReportUserPrefChanged() and GetMutableUserPref().
-  friend class subtle::ScopedUserPrefUpdateBase;
-  friend class PrefServiceTest_WriteablePrefStoreFlags_Test;
-
-  // Registration of pref change observers must be done using the
-  // PrefChangeRegistrar, which is declared as a friend here to grant it
-  // access to the otherwise protected members Add/RemovePrefObserver.
-  // PrefMember registers for preferences changes notification directly to
-  // avoid the storage overhead of the registrar, so its base class must be
-  // declared as a friend, too.
-  friend class PrefChangeRegistrar;
-  friend class subtle::PrefMemberBase;
-
-  // These are protected so they can only be accessed by the friend
-  // classes listed above.
-  //
-  // If the pref at the given path changes, we call the observer's
-  // OnPreferenceChanged method. Note that observers should not call
-  // these methods directly but rather use a PrefChangeRegistrar to
-  // make sure the observer gets cleaned up properly.
-  //
-  // Virtual for testing.
-  virtual void AddPrefObserver(const std::string& path, PrefObserver* obs);
-  virtual void RemovePrefObserver(const std::string& path, PrefObserver* obs);
-
-  // Sends notification of a changed preference. This needs to be called by
-  // a ScopedUserPrefUpdate if a DictionaryValue or ListValue is changed.
-  void ReportUserPrefChanged(const std::string& key);
-
-  // Sets the value for this pref path in the user pref store and informs the
-  // PrefNotifier of the change.
-  void SetUserPrefValue(const std::string& path, base::Value* new_value);
-
-  // Load preferences from storage, attempting to diagnose and handle errors.
-  // This should only be called from the constructor.
-  void InitFromStorage(bool async);
-
-  // Used to set the value of dictionary or list values in the user pref store.
-  // This will create a dictionary or list if one does not exist in the user
-  // pref store. This method returns NULL only if you're requesting an
-  // unregistered pref or a non-dict/non-list pref.
-  // |type| may only be Values::TYPE_DICTIONARY or Values::TYPE_LIST and
-  // |path| must point to a registered preference of type |type|.
-  // Ownership of the returned value remains at the user pref store.
-  base::Value* GetMutableUserPref(const std::string& path,
-                                  base::Value::Type type);
-
-  // GetPreferenceValue is the equivalent of FindPreference(path)->GetValue(),
-  // it has been added for performance. If is faster because it does
-  // not need to find or create a Preference object to get the
-  // value (GetValue() calls back though the preference service to
-  // actually get the value.).
-  const base::Value* GetPreferenceValue(const std::string& path) const;
-
-  // Local cache of registered Preference objects. The pref_registry_
-  // is authoritative with respect to what the types and default values
-  // of registered preferences are.
-  mutable PreferenceMap prefs_map_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefService);
-};
-
-#endif  // BASE_PREFS_PREF_SERVICE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_service.h"
diff --git a/base/prefs/pref_service_factory.h b/base/prefs/pref_service_factory.h
index f84e037..3bc4932 100644
--- a/base/prefs/pref_service_factory.h
+++ b/base/prefs/pref_service_factory.h
@@ -2,90 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_SERVICE_FACTORY_H_
-#define BASE_PREFS_PREF_SERVICE_FACTORY_H_
-
-#include "base/callback.h"
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/persistent_pref_store.h"
-#include "base/prefs/pref_registry.h"
-#include "base/prefs/pref_store.h"
-
-class PrefService;
-
-namespace base {
-
-class FilePath;
-class SequencedTaskRunner;
-
-// A class that allows convenient building of PrefService.
-class BASE_PREFS_EXPORT PrefServiceFactory {
- public:
-  PrefServiceFactory();
-  virtual ~PrefServiceFactory();
-
-  // Functions for setting the various parameters of the PrefService to build.
-  void set_managed_prefs(const scoped_refptr<PrefStore>& managed_prefs) {
-    managed_prefs_ = managed_prefs;
-  }
-  void set_supervised_user_prefs(
-      const scoped_refptr<PrefStore>& supervised_user_prefs) {
-    supervised_user_prefs_ = supervised_user_prefs;
-  }
-  void set_extension_prefs(const scoped_refptr<PrefStore>& extension_prefs) {
-    extension_prefs_ = extension_prefs;
-  }
-  void set_command_line_prefs(
-      const scoped_refptr<PrefStore>& command_line_prefs) {
-    command_line_prefs_ = command_line_prefs;
-  }
-  void set_user_prefs(const scoped_refptr<PersistentPrefStore>& user_prefs) {
-    user_prefs_ = user_prefs;
-  }
-  void set_recommended_prefs(
-      const scoped_refptr<PrefStore>& recommended_prefs) {
-    recommended_prefs_ = recommended_prefs;
-  }
-
-  // Sets up error callback for the PrefService.  A do-nothing default
-  // is provided if this is not called.
-  void set_read_error_callback(
-      const base::Callback<void(PersistentPrefStore::PrefReadError)>&
-          read_error_callback) {
-    read_error_callback_ = read_error_callback;
-  }
-
-  // Specifies to use an actual file-backed user pref store.
-  void SetUserPrefsFile(const base::FilePath& prefs_file,
-                        base::SequencedTaskRunner* task_runner);
-
-  void set_async(bool async) {
-    async_ = async;
-  }
-
-  // Creates a PrefService object initialized with the parameters from
-  // this factory.
-  scoped_ptr<PrefService> Create(PrefRegistry* registry);
-
- protected:
-  scoped_refptr<PrefStore> managed_prefs_;
-  scoped_refptr<PrefStore> supervised_user_prefs_;
-  scoped_refptr<PrefStore> extension_prefs_;
-  scoped_refptr<PrefStore> command_line_prefs_;
-  scoped_refptr<PersistentPrefStore> user_prefs_;
-  scoped_refptr<PrefStore> recommended_prefs_;
-
-  base::Callback<void(PersistentPrefStore::PrefReadError)> read_error_callback_;
-
-  // Defaults to false.
-  bool async_;
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(PrefServiceFactory);
-};
-
-}  // namespace base
-
-#endif  // BASE_PREFS_PREF_SERVICE_FACTORY_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_service_factory.h"
diff --git a/base/prefs/pref_store.h b/base/prefs/pref_store.h
index f95c8c42..c1c65839 100644
--- a/base/prefs/pref_store.h
+++ b/base/prefs/pref_store.h
@@ -2,62 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_STORE_H_
-#define BASE_PREFS_PREF_STORE_H_
-
-#include <string>
-
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/prefs/base_prefs_export.h"
-
-namespace base {
-class Value;
-}
-
-// This is an abstract interface for reading and writing from/to a persistent
-// preference store, used by PrefService. An implementation using a JSON file
-// can be found in JsonPrefStore, while an implementation without any backing
-// store for testing can be found in TestingPrefStore. Furthermore, there is
-// CommandLinePrefStore, which bridges command line options to preferences and
-// ConfigurationPolicyPrefStore, which is used for hooking up configuration
-// policy with the preference subsystem.
-class BASE_PREFS_EXPORT PrefStore : public base::RefCounted<PrefStore> {
- public:
-  // Observer interface for monitoring PrefStore.
-  class BASE_PREFS_EXPORT Observer {
-   public:
-    // Called when the value for the given |key| in the store changes.
-    virtual void OnPrefValueChanged(const std::string& key) = 0;
-    // Notification about the PrefStore being fully initialized.
-    virtual void OnInitializationCompleted(bool succeeded) = 0;
-
-   protected:
-    virtual ~Observer() {}
-  };
-
-  PrefStore() {}
-
-  // Add and remove observers.
-  virtual void AddObserver(Observer* observer) {}
-  virtual void RemoveObserver(Observer* observer) {}
-  virtual bool HasObservers() const;
-
-  // Whether the store has completed all asynchronous initialization.
-  virtual bool IsInitializationComplete() const;
-
-  // Get the value for a given preference |key| and stores it in |*result|.
-  // |*result| is only modified if the return value is true and if |result|
-  // is not NULL. Ownership of the |*result| value remains with the PrefStore.
-  virtual bool GetValue(const std::string& key,
-                        const base::Value** result) const = 0;
-
- protected:
-  friend class base::RefCounted<PrefStore>;
-  virtual ~PrefStore() {}
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(PrefStore);
-};
-
-#endif  // BASE_PREFS_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_store.h"
diff --git a/base/prefs/pref_store_observer_mock.h b/base/prefs/pref_store_observer_mock.h
index 1b24b4e0..be8e4d5 100644
--- a/base/prefs/pref_store_observer_mock.h
+++ b/base/prefs/pref_store_observer_mock.h
@@ -2,34 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
-#define BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
-
-#include <string>
-#include <vector>
-
-#include "base/compiler_specific.h"
-#include "base/macros.h"
-#include "base/prefs/pref_store.h"
-
-// A mock implementation of PrefStore::Observer.
-class PrefStoreObserverMock : public PrefStore::Observer {
- public:
-  PrefStoreObserverMock();
-  ~PrefStoreObserverMock() override;
-
-  void VerifyAndResetChangedKey(const std::string& expected);
-
-  // PrefStore::Observer implementation
-  void OnPrefValueChanged(const std::string& key) override;
-  void OnInitializationCompleted(bool success) override;
-
-  std::vector<std::string> changed_keys;
-  bool initialized;
-  bool initialization_success;  // Only valid if |initialized|.
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(PrefStoreObserverMock);
-};
-
-#endif  // BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_store_observer_mock.h"
diff --git a/base/prefs/pref_value_map.h b/base/prefs/pref_value_map.h
index 349fe68..e1ec94a 100644
--- a/base/prefs/pref_value_map.h
+++ b/base/prefs/pref_value_map.h
@@ -2,90 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_VALUE_MAP_H_
-#define BASE_PREFS_PREF_VALUE_MAP_H_
-
-#include <string>
-#include <vector>
-
-#include "base/containers/scoped_ptr_hash_map.h"
-#include "base/macros.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/prefs/base_prefs_export.h"
-
-namespace base {
-class Value;
-}
-
-// A generic string to value map used by the PrefStore implementations.
-class BASE_PREFS_EXPORT PrefValueMap {
- public:
-  using Map = base::ScopedPtrHashMap<std::string, scoped_ptr<base::Value>>;
-  using iterator = Map::iterator;
-  using const_iterator = Map::const_iterator;
-
-  PrefValueMap();
-  virtual ~PrefValueMap();
-
-  // Gets the value for |key| and stores it in |value|. Ownership remains with
-  // the map. Returns true if a value is present. If not, |value| is not
-  // touched.
-  bool GetValue(const std::string& key, const base::Value** value) const;
-  bool GetValue(const std::string& key, base::Value** value);
-
-  // Sets a new |value| for |key|. |value| must be non-null. Returns true if the
-  // value changed.
-  bool SetValue(const std::string& key, scoped_ptr<base::Value> value);
-
-  // Removes the value for |key| from the map. Returns true if a value was
-  // removed.
-  bool RemoveValue(const std::string& key);
-
-  // Clears the map.
-  void Clear();
-
-  // Swaps the contents of two maps.
-  void Swap(PrefValueMap* other);
-
-  iterator begin();
-  iterator end();
-  const_iterator begin() const;
-  const_iterator end() const;
-
-  // Gets a boolean value for |key| and stores it in |value|. Returns true if
-  // the value was found and of the proper type.
-  bool GetBoolean(const std::string& key, bool* value) const;
-
-  // Sets the value for |key| to the boolean |value|.
-  void SetBoolean(const std::string& key, bool value);
-
-  // Gets a string value for |key| and stores it in |value|. Returns true if
-  // the value was found and of the proper type.
-  bool GetString(const std::string& key, std::string* value) const;
-
-  // Sets the value for |key| to the string |value|.
-  void SetString(const std::string& key, const std::string& value);
-
-  // Gets an int value for |key| and stores it in |value|. Returns true if
-  // the value was found and of the proper type.
-  bool GetInteger(const std::string& key, int* value) const;
-
-  // Sets the value for |key| to the int |value|.
-  void SetInteger(const std::string& key, const int value);
-
-  // Sets the value for |key| to the double |value|.
-  void SetDouble(const std::string& key, const double value);
-
-  // Compares this value map against |other| and stores all key names that have
-  // different values in |differing_keys|. This includes keys that are present
-  // only in one of the maps.
-  void GetDifferingKeys(const PrefValueMap* other,
-                        std::vector<std::string>* differing_keys) const;
-
- private:
-  Map prefs_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefValueMap);
-};
-
-#endif  // BASE_PREFS_PREF_VALUE_MAP_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_value_map.h"
diff --git a/base/prefs/pref_value_store.h b/base/prefs/pref_value_store.h
index 8ec8c59..de10c56 100644
--- a/base/prefs/pref_value_store.h
+++ b/base/prefs/pref_value_store.h
@@ -2,259 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_PREF_VALUE_STORE_H_
-#define BASE_PREFS_PREF_VALUE_STORE_H_
-
-#include <map>
-#include <string>
-#include <vector>
-
-#include "base/callback.h"
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_store.h"
-#include "base/values.h"
-
-class PrefNotifier;
-class PrefStore;
-
-// The PrefValueStore manages various sources of values for Preferences
-// (e.g., configuration policies, extensions, and user settings). It returns
-// the value of a Preference from the source with the highest priority, and
-// allows setting user-defined values for preferences that are not managed.
-//
-// Unless otherwise explicitly noted, all of the methods of this class must
-// be called on the UI thread.
-class BASE_PREFS_EXPORT PrefValueStore {
- public:
-  typedef base::Callback<void(const std::string&)> PrefChangedCallback;
-
-  // In decreasing order of precedence:
-  //   |managed_prefs| contains all preferences from mandatory policies.
-  //   |supervised_user_prefs| contains all preferences from supervised user
-  //        settings, i.e. settings configured for a supervised user by their
-  //        custodian.
-  //   |extension_prefs| contains preference values set by extensions.
-  //   |command_line_prefs| contains preference values set by command-line
-  //        switches.
-  //   |user_prefs| contains all user-set preference values.
-  //   |recommended_prefs| contains all preferences from recommended policies.
-  //   |default_prefs| contains application-default preference values. It must
-  //        be non-null if any preferences are to be registered.
-  //
-  // |pref_notifier| facilitates broadcasting preference change notifications
-  // to the world.
-  PrefValueStore(PrefStore* managed_prefs,
-                 PrefStore* supervised_user_prefs,
-                 PrefStore* extension_prefs,
-                 PrefStore* command_line_prefs,
-                 PrefStore* user_prefs,
-                 PrefStore* recommended_prefs,
-                 PrefStore* default_prefs,
-                 PrefNotifier* pref_notifier);
-  virtual ~PrefValueStore();
-
-  // Creates a clone of this PrefValueStore with PrefStores overwritten
-  // by the parameters passed, if unequal NULL.
-  PrefValueStore* CloneAndSpecialize(PrefStore* managed_prefs,
-                                     PrefStore* supervised_user_prefs,
-                                     PrefStore* extension_prefs,
-                                     PrefStore* command_line_prefs,
-                                     PrefStore* user_prefs,
-                                     PrefStore* recommended_prefs,
-                                     PrefStore* default_prefs,
-                                     PrefNotifier* pref_notifier);
-
-  // A PrefValueStore can have exactly one callback that is directly
-  // notified of preferences changing in the store. This does not
-  // filter through the PrefNotifier mechanism, which may not forward
-  // certain changes (e.g. unregistered prefs).
-  void set_callback(const PrefChangedCallback& callback);
-
-  // Gets the value for the given preference name that has the specified value
-  // type. Values stored in a PrefStore that have the matching |name| but
-  // a non-matching |type| are silently skipped. Returns true if a valid value
-  // was found in any of the available PrefStores. Most callers should use
-  // Preference::GetValue() instead of calling this method directly.
-  bool GetValue(const std::string& name,
-                base::Value::Type type,
-                const base::Value** out_value) const;
-
-  // Gets the recommended value for the given preference name that has the
-  // specified value type. A value stored in the recommended PrefStore that has
-  // the matching |name| but a non-matching |type| is silently ignored. Returns
-  // true if a valid value was found. Most callers should use
-  // Preference::GetRecommendedValue() instead of calling this method directly.
-  bool GetRecommendedValue(const std::string& name,
-                           base::Value::Type type,
-                           const base::Value** out_value) const;
-
-  // These methods return true if a preference with the given name is in the
-  // indicated pref store, even if that value is currently being overridden by
-  // a higher-priority source.
-  bool PrefValueInManagedStore(const std::string& name) const;
-  bool PrefValueInSupervisedStore(const std::string& name) const;
-  bool PrefValueInExtensionStore(const std::string& name) const;
-  bool PrefValueInUserStore(const std::string& name) const;
-
-  // These methods return true if a preference with the given name is actually
-  // being controlled by the indicated pref store and not being overridden by
-  // a higher-priority source.
-  bool PrefValueFromExtensionStore(const std::string& name) const;
-  bool PrefValueFromUserStore(const std::string& name) const;
-  bool PrefValueFromRecommendedStore(const std::string& name) const;
-  bool PrefValueFromDefaultStore(const std::string& name) const;
-
-  // Check whether a Preference value is modifiable by the user, i.e. whether
-  // there is no higher-priority source controlling it.
-  bool PrefValueUserModifiable(const std::string& name) const;
-
-  // Check whether a Preference value is modifiable by an extension, i.e.
-  // whether there is no higher-priority source controlling it.
-  bool PrefValueExtensionModifiable(const std::string& name) const;
-
-  // Update the command line PrefStore with |command_line_prefs|.
-  void UpdateCommandLinePrefStore(PrefStore* command_line_prefs);
-
- private:
-  // PrefStores must be listed here in order from highest to lowest priority.
-  //   MANAGED contains all managed preference values that are provided by
-  //      mandatory policies (e.g. Windows Group Policy or cloud policy).
-  //   SUPERVISED_USER contains preferences that are valid for supervised users.
-  //   EXTENSION contains preference values set by extensions.
-  //   COMMAND_LINE contains preference values set by command-line switches.
-  //   USER contains all user-set preference values.
-  //   RECOMMENDED contains all preferences that are provided by recommended
-  //      policies.
-  //   DEFAULT contains all application default preference values.
-  enum PrefStoreType {
-    // INVALID_STORE is not associated with an actual PrefStore but used as
-    // an invalid marker, e.g. as a return value.
-    INVALID_STORE = -1,
-    MANAGED_STORE = 0,
-    SUPERVISED_USER_STORE,
-    EXTENSION_STORE,
-    COMMAND_LINE_STORE,
-    USER_STORE,
-    RECOMMENDED_STORE,
-    DEFAULT_STORE,
-    PREF_STORE_TYPE_MAX = DEFAULT_STORE
-  };
-
-  // Keeps a PrefStore reference on behalf of the PrefValueStore and monitors
-  // the PrefStore for changes, forwarding notifications to PrefValueStore. This
-  // indirection is here for the sake of disambiguating notifications from the
-  // individual PrefStores.
-  class PrefStoreKeeper : public PrefStore::Observer {
-   public:
-    PrefStoreKeeper();
-    ~PrefStoreKeeper() override;
-
-    // Takes ownership of |pref_store|.
-    void Initialize(PrefValueStore* store,
-                    PrefStore* pref_store,
-                    PrefStoreType type);
-
-    PrefStore* store() { return pref_store_.get(); }
-    const PrefStore* store() const { return pref_store_.get(); }
-
-   private:
-    // PrefStore::Observer implementation.
-    void OnPrefValueChanged(const std::string& key) override;
-    void OnInitializationCompleted(bool succeeded) override;
-
-    // PrefValueStore this keeper is part of.
-    PrefValueStore* pref_value_store_;
-
-    // The PrefStore managed by this keeper.
-    scoped_refptr<PrefStore> pref_store_;
-
-    // Type of the pref store.
-    PrefStoreType type_;
-
-    DISALLOW_COPY_AND_ASSIGN(PrefStoreKeeper);
-  };
-
-  typedef std::map<std::string, base::Value::Type> PrefTypeMap;
-
-  // Returns true if the preference with the given name has a value in the
-  // given PrefStoreType, of the same value type as the preference was
-  // registered with.
-  bool PrefValueInStore(const std::string& name, PrefStoreType store) const;
-
-  // Returns true if a preference has an explicit value in any of the
-  // stores in the range specified by |first_checked_store| and
-  // |last_checked_store|, even if that value is currently being
-  // overridden by a higher-priority store.
-  bool PrefValueInStoreRange(const std::string& name,
-                             PrefStoreType first_checked_store,
-                             PrefStoreType last_checked_store) const;
-
-  // Returns the pref store type identifying the source that controls the
-  // Preference identified by |name|. If none of the sources has a value,
-  // INVALID_STORE is returned. In practice, the default PrefStore
-  // should always have a value for any registered preferencem, so INVALID_STORE
-  // indicates an error.
-  PrefStoreType ControllingPrefStoreForPref(const std::string& name) const;
-
-  // Get a value from the specified |store|.
-  bool GetValueFromStore(const std::string& name,
-                         PrefStoreType store,
-                         const base::Value** out_value) const;
-
-  // Get a value from the specified |store| if its |type| matches.
-  bool GetValueFromStoreWithType(const std::string& name,
-                                 base::Value::Type type,
-                                 PrefStoreType store,
-                                 const base::Value** out_value) const;
-
-  // Called upon changes in individual pref stores in order to determine whether
-  // the user-visible pref value has changed. Triggers the change notification
-  // if the effective value of the preference has changed, or if the store
-  // controlling the pref has changed.
-  void NotifyPrefChanged(const std::string& path, PrefStoreType new_store);
-
-  // Called from the PrefStoreKeeper implementation when a pref value for |key|
-  // changed in the pref store for |type|.
-  void OnPrefValueChanged(PrefStoreType type, const std::string& key);
-
-  // Handle the event that the store for |type| has completed initialization.
-  void OnInitializationCompleted(PrefStoreType type, bool succeeded);
-
-  // Initializes a pref store keeper. Sets up a PrefStoreKeeper that will take
-  // ownership of the passed |pref_store|.
-  void InitPrefStore(PrefStoreType type, PrefStore* pref_store);
-
-  // Checks whether initialization is completed and tells the notifier if that
-  // is the case.
-  void CheckInitializationCompleted();
-
-  // Get the PrefStore pointer for the given type. May return NULL if there is
-  // no PrefStore for that type.
-  PrefStore* GetPrefStore(PrefStoreType type) {
-    return pref_stores_[type].store();
-  }
-  const PrefStore* GetPrefStore(PrefStoreType type) const {
-    return pref_stores_[type].store();
-  }
-
-  // Keeps the PrefStore references in order of precedence.
-  PrefStoreKeeper pref_stores_[PREF_STORE_TYPE_MAX + 1];
-
-  PrefChangedCallback pref_changed_callback_;
-
-  // Used for generating notifications. This is a weak reference,
-  // since the notifier is owned by the corresponding PrefService.
-  PrefNotifier* pref_notifier_;
-
-  // A mapping of preference names to their registered types.
-  PrefTypeMap pref_types_;
-
-  // True if not all of the PrefStores were initialized successfully.
-  bool initialization_failed_;
-
-  DISALLOW_COPY_AND_ASSIGN(PrefValueStore);
-};
-
-#endif  // BASE_PREFS_PREF_VALUE_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/pref_value_store.h"
diff --git a/base/prefs/scoped_user_pref_update.h b/base/prefs/scoped_user_pref_update.h
index 29ad852..ce03c6a8 100644
--- a/base/prefs/scoped_user_pref_update.h
+++ b/base/prefs/scoped_user_pref_update.h
@@ -1,108 +1,7 @@
 // Copyright 2013 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
-//
-// A helper class that assists preferences in firing notifications when lists
-// or dictionaries are changed.
 
-#ifndef BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
-#define BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
-
-#include <string>
-
-#include "base/macros.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_service.h"
-#include "base/threading/non_thread_safe.h"
-#include "base/values.h"
-
-class PrefService;
-
-namespace base {
-class DictionaryValue;
-class ListValue;
-}
-
-namespace subtle {
-
-// Base class for ScopedUserPrefUpdateTemplate that contains the parts
-// that do not depend on ScopedUserPrefUpdateTemplate's template parameter.
-//
-// We need this base class mostly for making it a friend of PrefService
-// and getting access to PrefService::GetMutableUserPref and
-// PrefService::ReportUserPrefChanged.
-class BASE_PREFS_EXPORT ScopedUserPrefUpdateBase : public base::NonThreadSafe {
- protected:
-  ScopedUserPrefUpdateBase(PrefService* service, const std::string& path);
-
-  // Calls Notify().
-  ~ScopedUserPrefUpdateBase();
-
-  // Sets |value_| to |service_|->GetMutableUserPref and returns it.
-  base::Value* GetValueOfType(base::Value::Type type);
-
- private:
-  // If |value_| is not null, triggers a notification of PrefObservers and
-  // resets |value_|.
-  void Notify();
-
-  // Weak pointer.
-  PrefService* service_;
-  // Path of the preference being updated.
-  std::string path_;
-  // Cache of value from user pref store (set between Get() and Notify() calls).
-  base::Value* value_;
-
-  DISALLOW_COPY_AND_ASSIGN(ScopedUserPrefUpdateBase);
-};
-
-}  // namespace subtle
-
-// Class to support modifications to DictionaryValues and ListValues while
-// guaranteeing that PrefObservers are notified of changed values.
-//
-// This class may only be used on the UI thread as it requires access to the
-// PrefService.
-template <typename T, base::Value::Type type_enum_value>
-class ScopedUserPrefUpdate : public subtle::ScopedUserPrefUpdateBase {
- public:
-  ScopedUserPrefUpdate(PrefService* service, const std::string& path)
-      : ScopedUserPrefUpdateBase(service, path) {}
-
-  // Triggers an update notification if Get() was called.
-  virtual ~ScopedUserPrefUpdate() {}
-
-  // Returns a mutable |T| instance that
-  // - is already in the user pref store, or
-  // - is (silently) created and written to the user pref store if none existed
-  //   before.
-  //
-  // Calling Get() implies that an update notification is necessary at
-  // destruction time.
-  //
-  // The ownership of the return value remains with the user pref store.
-  // Virtual so it can be overriden in subclasses that transform the value
-  // before returning it (for example to return a subelement of a dictionary).
-  virtual T* Get() {
-    return static_cast<T*>(GetValueOfType(type_enum_value));
-  }
-
-  T& operator*() {
-    return *Get();
-  }
-
-  T* operator->() {
-    return Get();
-  }
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(ScopedUserPrefUpdate);
-};
-
-typedef ScopedUserPrefUpdate<base::DictionaryValue,
-                             base::Value::TYPE_DICTIONARY>
-    DictionaryPrefUpdate;
-typedef ScopedUserPrefUpdate<base::ListValue, base::Value::TYPE_LIST>
-    ListPrefUpdate;
-
-#endif  // BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/scoped_user_pref_update.h"
diff --git a/base/prefs/testing_pref_service.h b/base/prefs/testing_pref_service.h
index 85a2879..c60b89e 100644
--- a/base/prefs/testing_pref_service.h
+++ b/base/prefs/testing_pref_service.h
@@ -2,195 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_TESTING_PREF_SERVICE_H_
-#define BASE_PREFS_TESTING_PREF_SERVICE_H_
-
-#include "base/macros.h"
-#include "base/memory/ref_counted.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/prefs/pref_registry.h"
-#include "base/prefs/pref_service.h"
-#include "base/prefs/testing_pref_store.h"
-
-class PrefNotifierImpl;
-class PrefRegistrySimple;
-class TestingPrefStore;
-
-// A PrefService subclass for testing. It operates totally in memory and
-// provides additional API for manipulating preferences at the different levels
-// (managed, extension, user) conveniently.
-//
-// Use this via its specializations, e.g. TestingPrefServiceSimple.
-template <class SuperPrefService, class ConstructionPrefRegistry>
-class TestingPrefServiceBase : public SuperPrefService {
- public:
-  virtual ~TestingPrefServiceBase();
-
-  // Read the value of a preference from the managed layer. Returns NULL if the
-  // preference is not defined at the managed layer.
-  const base::Value* GetManagedPref(const std::string& path) const;
-
-  // Set a preference on the managed layer and fire observers if the preference
-  // changed. Assumes ownership of |value|.
-  void SetManagedPref(const std::string& path, base::Value* value);
-
-  // Clear the preference on the managed layer and fire observers if the
-  // preference has been defined previously.
-  void RemoveManagedPref(const std::string& path);
-
-  // Similar to the above, but for user preferences.
-  const base::Value* GetUserPref(const std::string& path) const;
-  void SetUserPref(const std::string& path, base::Value* value);
-  void RemoveUserPref(const std::string& path);
-
-  // Similar to the above, but for recommended policy preferences.
-  const base::Value* GetRecommendedPref(const std::string& path) const;
-  void SetRecommendedPref(const std::string& path, base::Value* value);
-  void RemoveRecommendedPref(const std::string& path);
-
-  // Do-nothing implementation for TestingPrefService.
-  static void HandleReadError(PersistentPrefStore::PrefReadError error) {}
-
- protected:
-  TestingPrefServiceBase(
-      TestingPrefStore* managed_prefs,
-      TestingPrefStore* user_prefs,
-      TestingPrefStore* recommended_prefs,
-      ConstructionPrefRegistry* pref_registry,
-      PrefNotifierImpl* pref_notifier);
-
- private:
-  // Reads the value of the preference indicated by |path| from |pref_store|.
-  // Returns NULL if the preference was not found.
-  const base::Value* GetPref(TestingPrefStore* pref_store,
-                             const std::string& path) const;
-
-  // Sets the value for |path| in |pref_store|.
-  void SetPref(TestingPrefStore* pref_store,
-               const std::string& path,
-               base::Value* value);
-
-  // Removes the preference identified by |path| from |pref_store|.
-  void RemovePref(TestingPrefStore* pref_store, const std::string& path);
-
-  // Pointers to the pref stores our value store uses.
-  scoped_refptr<TestingPrefStore> managed_prefs_;
-  scoped_refptr<TestingPrefStore> user_prefs_;
-  scoped_refptr<TestingPrefStore> recommended_prefs_;
-
-  DISALLOW_COPY_AND_ASSIGN(TestingPrefServiceBase);
-};
-
-// Test version of PrefService.
-class TestingPrefServiceSimple
-    : public TestingPrefServiceBase<PrefService, PrefRegistry> {
- public:
-  TestingPrefServiceSimple();
-  ~TestingPrefServiceSimple() override;
-
-  // This is provided as a convenience for registering preferences on
-  // an existing TestingPrefServiceSimple instance. On a production
-  // PrefService you would do all registrations before constructing
-  // it, passing it a PrefRegistry via its constructor (or via
-  // e.g. PrefServiceFactory).
-  PrefRegistrySimple* registry();
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(TestingPrefServiceSimple);
-};
-
-template<>
-TestingPrefServiceBase<PrefService, PrefRegistry>::TestingPrefServiceBase(
-    TestingPrefStore* managed_prefs,
-    TestingPrefStore* user_prefs,
-    TestingPrefStore* recommended_prefs,
-    PrefRegistry* pref_registry,
-    PrefNotifierImpl* pref_notifier);
-
-template<class SuperPrefService, class ConstructionPrefRegistry>
-TestingPrefServiceBase<
-    SuperPrefService, ConstructionPrefRegistry>::~TestingPrefServiceBase() {
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-const base::Value* TestingPrefServiceBase<
-    SuperPrefService,
-    ConstructionPrefRegistry>::GetManagedPref(const std::string& path) const {
-  return GetPref(managed_prefs_.get(), path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    SetManagedPref(const std::string& path, base::Value* value) {
-  SetPref(managed_prefs_.get(), path, value);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    RemoveManagedPref(const std::string& path) {
-  RemovePref(managed_prefs_.get(), path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-const base::Value*
-TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::GetUserPref(
-    const std::string& path) const {
-  return GetPref(user_prefs_.get(), path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    SetUserPref(const std::string& path, base::Value* value) {
-  SetPref(user_prefs_.get(), path, value);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    RemoveUserPref(const std::string& path) {
-  RemovePref(user_prefs_.get(), path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-const base::Value*
-TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    GetRecommendedPref(const std::string& path) const {
-  return GetPref(recommended_prefs_, path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    SetRecommendedPref(const std::string& path, base::Value* value) {
-  SetPref(recommended_prefs_.get(), path, value);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    RemoveRecommendedPref(const std::string& path) {
-  RemovePref(recommended_prefs_.get(), path);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-const base::Value*
-TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::GetPref(
-    TestingPrefStore* pref_store,
-    const std::string& path) const {
-  const base::Value* res;
-  return pref_store->GetValue(path, &res) ? res : NULL;
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    SetPref(TestingPrefStore* pref_store,
-            const std::string& path,
-            base::Value* value) {
-  pref_store->SetValue(path, make_scoped_ptr(value),
-                       WriteablePrefStore::DEFAULT_PREF_WRITE_FLAGS);
-}
-
-template <class SuperPrefService, class ConstructionPrefRegistry>
-void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
-    RemovePref(TestingPrefStore* pref_store, const std::string& path) {
-  pref_store->RemoveValue(path, WriteablePrefStore::DEFAULT_PREF_WRITE_FLAGS);
-}
-
-#endif  // BASE_PREFS_TESTING_PREF_SERVICE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/testing_pref_service.h"
diff --git a/base/prefs/testing_pref_store.h b/base/prefs/testing_pref_store.h
index 713e69a7..297aa116 100644
--- a/base/prefs/testing_pref_store.h
+++ b/base/prefs/testing_pref_store.h
@@ -2,113 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_TESTING_PREF_STORE_H_
-#define BASE_PREFS_TESTING_PREF_STORE_H_
-
-#include <stdint.h>
-
-#include <string>
-
-#include "base/compiler_specific.h"
-#include "base/macros.h"
-#include "base/observer_list.h"
-#include "base/prefs/persistent_pref_store.h"
-#include "base/prefs/pref_value_map.h"
-
-// |TestingPrefStore| is a preference store implementation that allows tests to
-// explicitly manipulate the contents of the store, triggering notifications
-// where appropriate.
-class TestingPrefStore : public PersistentPrefStore {
- public:
-  TestingPrefStore();
-
-  // Overriden from PrefStore.
-  bool GetValue(const std::string& key,
-                const base::Value** result) const override;
-  void AddObserver(PrefStore::Observer* observer) override;
-  void RemoveObserver(PrefStore::Observer* observer) override;
-  bool HasObservers() const override;
-  bool IsInitializationComplete() const override;
-
-  // PersistentPrefStore overrides:
-  bool GetMutableValue(const std::string& key, base::Value** result) override;
-  void ReportValueChanged(const std::string& key, uint32_t flags) override;
-  void SetValue(const std::string& key,
-                scoped_ptr<base::Value> value,
-                uint32_t flags) override;
-  void SetValueSilently(const std::string& key,
-                        scoped_ptr<base::Value> value,
-                        uint32_t flags) override;
-  void RemoveValue(const std::string& key, uint32_t flags) override;
-  bool ReadOnly() const override;
-  PrefReadError GetReadError() const override;
-  PersistentPrefStore::PrefReadError ReadPrefs() override;
-  void ReadPrefsAsync(ReadErrorDelegate* error_delegate) override;
-  void CommitPendingWrite() override;
-  void SchedulePendingLossyWrites() override;
-
-  // Marks the store as having completed initialization.
-  void SetInitializationCompleted();
-
-  // Used for tests to trigger notifications explicitly.
-  void NotifyPrefValueChanged(const std::string& key);
-  void NotifyInitializationCompleted();
-
-  // Some convenience getters/setters.
-  void SetString(const std::string& key, const std::string& value);
-  void SetInteger(const std::string& key, int value);
-  void SetBoolean(const std::string& key, bool value);
-
-  bool GetString(const std::string& key, std::string* value) const;
-  bool GetInteger(const std::string& key, int* value) const;
-  bool GetBoolean(const std::string& key, bool* value) const;
-
-  // Determines whether ReadPrefsAsync completes immediately. Defaults to false
-  // (non-blocking). To block, invoke this with true (blocking) before the call
-  // to ReadPrefsAsync. To unblock, invoke again with false (non-blocking) after
-  // the call to ReadPrefsAsync.
-  void SetBlockAsyncRead(bool block_async_read);
-
-  // Getter and Setter methods for setting and getting the state of the
-  // |TestingPrefStore|.
-  virtual void set_read_only(bool read_only);
-  void set_read_success(bool read_success);
-  void set_read_error(PersistentPrefStore::PrefReadError read_error);
-  bool committed() { return committed_; }
-
- protected:
-  ~TestingPrefStore() override;
-
- private:
-  // Stores the preference values.
-  PrefValueMap prefs_;
-
-  // Flag that indicates if the PrefStore is read-only
-  bool read_only_;
-
-  // The result to pass to PrefStore::Observer::OnInitializationCompleted
-  bool read_success_;
-
-  // The result to return from ReadPrefs or ReadPrefsAsync.
-  PersistentPrefStore::PrefReadError read_error_;
-
-  // Whether a call to ReadPrefsAsync should block.
-  bool block_async_read_;
-
-  // Whether there is a pending call to ReadPrefsAsync.
-  bool pending_async_read_;
-
-  // Whether initialization has been completed.
-  bool init_complete_;
-
-  // Whether the store contents have been committed to disk since the last
-  // mutation.
-  bool committed_;
-
-  scoped_ptr<ReadErrorDelegate> error_delegate_;
-  base::ObserverList<PrefStore::Observer, true> observers_;
-
-  DISALLOW_COPY_AND_ASSIGN(TestingPrefStore);
-};
-
-#endif  // BASE_PREFS_TESTING_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/testing_pref_store.h"
diff --git a/base/prefs/value_map_pref_store.h b/base/prefs/value_map_pref_store.h
index eac785d..4373ff7 100644
--- a/base/prefs/value_map_pref_store.h
+++ b/base/prefs/value_map_pref_store.h
@@ -2,56 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_VALUE_MAP_PREF_STORE_H_
-#define BASE_PREFS_VALUE_MAP_PREF_STORE_H_
-
-#include <stdint.h>
-
-#include <map>
-#include <string>
-
-#include "base/macros.h"
-#include "base/observer_list.h"
-#include "base/prefs/base_prefs_export.h"
-#include "base/prefs/pref_value_map.h"
-#include "base/prefs/writeable_pref_store.h"
-
-// A basic PrefStore implementation that uses a simple name-value map for
-// storing the preference values.
-class BASE_PREFS_EXPORT ValueMapPrefStore : public WriteablePrefStore {
- public:
-  ValueMapPrefStore();
-
-  // PrefStore overrides:
-  bool GetValue(const std::string& key,
-                const base::Value** value) const override;
-  void AddObserver(PrefStore::Observer* observer) override;
-  void RemoveObserver(PrefStore::Observer* observer) override;
-  bool HasObservers() const override;
-
-  // WriteablePrefStore overrides:
-  void SetValue(const std::string& key,
-                scoped_ptr<base::Value> value,
-                uint32_t flags) override;
-  void RemoveValue(const std::string& key, uint32_t flags) override;
-  bool GetMutableValue(const std::string& key, base::Value** value) override;
-  void ReportValueChanged(const std::string& key, uint32_t flags) override;
-  void SetValueSilently(const std::string& key,
-                        scoped_ptr<base::Value> value,
-                        uint32_t flags) override;
-
- protected:
-  ~ValueMapPrefStore() override;
-
-  // Notify observers about the initialization completed event.
-  void NotifyInitializationCompleted();
-
- private:
-  PrefValueMap prefs_;
-
-  base::ObserverList<PrefStore::Observer, true> observers_;
-
-  DISALLOW_COPY_AND_ASSIGN(ValueMapPrefStore);
-};
-
-#endif  // BASE_PREFS_VALUE_MAP_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/value_map_pref_store.h"
diff --git a/base/prefs/writeable_pref_store.h b/base/prefs/writeable_pref_store.h
index f7da279a..69bd2cb 100644
--- a/base/prefs/writeable_pref_store.h
+++ b/base/prefs/writeable_pref_store.h
@@ -2,71 +2,6 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#ifndef BASE_PREFS_WRITEABLE_PREF_STORE_H_
-#define BASE_PREFS_WRITEABLE_PREF_STORE_H_
-
-#include <stdint.h>
-
-#include <string>
-
-#include "base/macros.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/prefs/pref_store.h"
-
-namespace base {
-class Value;
-}
-
-// A pref store that can be written to as well as read from.
-class BASE_PREFS_EXPORT WriteablePrefStore : public PrefStore {
- public:
-  // PrefWriteFlags can be used to change the way a pref will be written to
-  // storage.
-  enum PrefWriteFlags : uint32_t {
-    // No flags are specified.
-    DEFAULT_PREF_WRITE_FLAGS = 0,
-
-    // This marks the pref as "lossy". There is no strict time guarantee on when
-    // a lossy pref will be persisted to permanent storage when it is modified.
-    LOSSY_PREF_WRITE_FLAG = 1 << 1
-  };
-
-  WriteablePrefStore() {}
-
-  // Sets a |value| for |key| in the store. |value| must be non-NULL. |flags| is
-  // a bitmask of PrefWriteFlags.
-  virtual void SetValue(const std::string& key,
-                        scoped_ptr<base::Value> value,
-                        uint32_t flags) = 0;
-
-  // Removes the value for |key|.
-  virtual void RemoveValue(const std::string& key, uint32_t flags) = 0;
-
-  // Equivalent to PrefStore::GetValue but returns a mutable value.
-  virtual bool GetMutableValue(const std::string& key,
-                               base::Value** result) = 0;
-
-  // Triggers a value changed notification. This function needs to be called
-  // if one retrieves a list or dictionary with GetMutableValue and change its
-  // value. SetValue takes care of notifications itself. Note that
-  // ReportValueChanged will trigger notifications even if nothing has changed.
-  // |flags| is a bitmask of PrefWriteFlags.
-  virtual void ReportValueChanged(const std::string& key, uint32_t flags) = 0;
-
-  // Same as SetValue, but doesn't generate notifications. This is used by
-  // PrefService::GetMutableUserPref() in order to put empty entries
-  // into the user pref store. Using SetValue is not an option since existing
-  // tests rely on the number of notifications generated. |flags| is a bitmask
-  // of PrefWriteFlags.
-  virtual void SetValueSilently(const std::string& key,
-                                scoped_ptr<base::Value> value,
-                                uint32_t flags) = 0;
-
- protected:
-  ~WriteablePrefStore() override {}
-
- private:
-  DISALLOW_COPY_AND_ASSIGN(WriteablePrefStore);
-};
-
-#endif  // BASE_PREFS_WRITEABLE_PREF_STORE_H_
+// TODO(brettw) remove this forwarding header when prefs is completely moved to
+// components.
+#include "components/prefs/writeable_pref_store.h"
diff --git a/base/test/data/prefs/invalid.json b/base/test/data/prefs/invalid.json
deleted file mode 100644
index 43392a92..0000000
--- a/base/test/data/prefs/invalid.json
+++ /dev/null
@@ -1 +0,0 @@
-!@#$%^&
\ No newline at end of file
diff --git a/base/test/data/prefs/read.json b/base/test/data/prefs/read.json
deleted file mode 100644
index ea578a47..0000000
--- a/base/test/data/prefs/read.json
+++ /dev/null
@@ -1,8 +0,0 @@
-{
-  "homepage": "http://www.cnn.com",
-  "some_directory": "/usr/local/",
-  "tabs": {
-    "new_windows_in_tabs": true,
-    "max_tabs": 20
-  }
-}
diff --git a/base/test/data/prefs/write.golden.json b/base/test/data/prefs/write.golden.json
deleted file mode 100644
index fb1fff1..0000000
--- a/base/test/data/prefs/write.golden.json
+++ /dev/null
@@ -1 +0,0 @@
-{"homepage":"http://www.cnn.com","long_int":{"pref":"214748364842"},"some_directory":"/usr/sbin/","tabs":{"max_tabs":10,"new_windows_in_tabs":false}}
\ No newline at end of file
diff --git a/build/common.gypi b/build/common.gypi
index ceda6a2f..40bb44ed5 100644
--- a/build/common.gypi
+++ b/build/common.gypi
@@ -3112,6 +3112,11 @@
         # TODO: Enable on Windows too, http://crbug.com/404525
         'variables': { 'clang_warning_flags': ['-Wexit-time-destructors']},
       }],
+      ['"<!(python <(DEPTH)/tools/clang/scripts/update.py --print-revision)"!="257955-1"', {
+        # TODO(thakis): Remove once
+        # https://chromium-review.googlesource.com/#/c/324860/ is in.
+        'variables': { 'clang_warning_flags': ['-Wno-constant-conversion']},
+      }],
       ['chromium_code==0', {
         'variables': {
           'clang_warning_flags': [
diff --git a/build/config/compiler/BUILD.gn b/build/config/compiler/BUILD.gn
index cf7a288..6c5bdc8 100644
--- a/build/config/compiler/BUILD.gn
+++ b/build/config/compiler/BUILD.gn
@@ -883,6 +883,16 @@
         "-Wno-shift-negative-value",
       ]
     }
+
+    if (exec_script("//tools/clang/scripts/update.py",
+                    [ "--print-revision" ],
+                    "trim string") != "257955-1") {
+      cflags += [
+        # TODO(thakis): Remove once
+        # https://chromium-review.googlesource.com/#/c/324860/ is in.
+        "-Wno-constant-conversion",
+      ]
+    }
   }
 }
 
diff --git a/build/secondary/third_party/nss/BUILD.gn b/build/secondary/third_party/nss/BUILD.gn
index 7b32a04..2dc414d 100644
--- a/build/secondary/third_party/nss/BUILD.gn
+++ b/build/secondary/third_party/nss/BUILD.gn
@@ -474,6 +474,30 @@
     ]
   }
 
+  config("nss_static_config_private") {
+    if (is_clang) {
+      cflags = [
+        # nss doesn"t explicitly cast between different enum types.
+        "-Wno-conversion",
+
+        # nss passes "const char*" through "void*".
+        "-Wno-incompatible-pointer-types",
+
+        # nss prefers `a && b || c` over `(a && b) || c`.
+        "-Wno-logical-op-parentheses",
+
+        # nss doesn"t use exhaustive switches on enums
+        "-Wno-switch",
+
+        # nss has some `unsigned < 0` checks.
+        "-Wno-tautological-compare",
+
+        # nss-urandom-abort.patch removed the only call to rng_systemFromNoise
+        "-Wno-unused-function",
+      ]
+    }
+  }
+
   if (is_win && current_cpu == "x86") {
     source_set("nss_static_avx") {
       sources = [
@@ -891,6 +915,7 @@
 
       # nss passes "const char*" through "void*".
       "//build/config/compiler:no_incompatible_pointer_warnings",
+      ":nss_static_config_private",
     ]
     public_configs = [ ":nss_static_config" ]
 
@@ -1183,28 +1208,6 @@
       ]
     }
 
-    if (is_clang) {
-      cflags += [
-        # nss doesn"t explicitly cast between different enum types.
-        "-Wno-conversion",
-
-        # nss passes "const char*" through "void*".
-        "-Wno-incompatible-pointer-types",
-
-        # nss prefers `a && b || c` over `(a && b) || c`.
-        "-Wno-logical-op-parentheses",
-
-        # nss doesn"t use exhaustive switches on enums
-        "-Wno-switch",
-
-        # nss has some `unsigned < 0` checks.
-        "-Wno-tautological-compare",
-
-        # nss-urandom-abort.patch removed the only call to rng_systemFromNoise
-        "-Wno-unused-function",
-      ]
-    }
-
     public_deps = [
       ":nspr",
     ]
diff --git a/chrome/VERSION b/chrome/VERSION
index 34ad8ef..c010ed29 100644
--- a/chrome/VERSION
+++ b/chrome/VERSION
@@ -1,4 +1,4 @@
 MAJOR=50
 MINOR=0
-BUILD=2635
+BUILD=2636
 PATCH=0
diff --git a/chrome/browser/BUILD.gn b/chrome/browser/BUILD.gn
index bb999334..47f1ce02 100644
--- a/chrome/browser/BUILD.gn
+++ b/chrome/browser/BUILD.gn
@@ -1130,7 +1130,6 @@
     "//chrome/browser/ui:test_support",
   ]
   deps = [
-    "//base:prefs_test_support",
     "//chrome/app/theme:theme_resources",
     "//chrome/browser",
     "//chrome/common",
@@ -1139,6 +1138,7 @@
     "//components/invalidation/impl",
     "//components/invalidation/impl:test_support",
     "//components/password_manager/core/browser:test_support",
+    "//components/prefs:test_support",
     "//components/search_engines:test_support",
     "//components/syncable_prefs:test_support",
     "//components/user_prefs/tracked:user_prefs_tracked_test_support",
diff --git a/chrome/browser/resources/settings/compiled_resources.gyp b/chrome/browser/resources/settings/compiled_resources.gyp
index a76bc54..a124922 100644
--- a/chrome/browser/resources/settings/compiled_resources.gyp
+++ b/chrome/browser/resources/settings/compiled_resources.gyp
@@ -7,19 +7,20 @@
       'target_name': 'settings_resources',
       'type': 'none',
       'dependencies': [
-        'appearance_page/compiled_resources.gyp:*',
         'advanced_page/compiled_resources.gyp:*',
+        'appearance_page/compiled_resources.gyp:*',
         'basic_page/compiled_resources.gyp:*',
         'bluetooth_page/compiled_resources.gyp:*',
+        'controls/compiled_resources.gyp:*',
         'internet_page/compiled_resources.gyp:*',
         'languages_page/compiled_resources.gyp:*',
         'on_startup_page/compiled_resources.gyp:*',
+        'passwords_and_forms_page/compiled_resources.gyp:*',
         'people_page/compiled_resources.gyp:*',
         'prefs/compiled_resources.gyp:*',
         'settings_page/compiled_resources.gyp:*',
         'site_settings/compiled_resources.gyp:*',
         'site_settings_page/compiled_resources.gyp:*',
-        'controls/compiled_resources.gyp:*',
       ],
     },
   ]
diff --git a/chrome/browser/resources/settings/passwords_and_forms_page/compiled_resources.gyp b/chrome/browser/resources/settings/passwords_and_forms_page/compiled_resources.gyp
new file mode 100644
index 0000000..997c1b2
--- /dev/null
+++ b/chrome/browser/resources/settings/passwords_and_forms_page/compiled_resources.gyp
@@ -0,0 +1,26 @@
+# Copyright 2016 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+{
+  'targets': [
+    {
+      'target_name': 'passwords_and_forms_page',
+      'variables': {
+        'depends': [
+          'compiled_resources.gyp:passwords_section',
+          '../../../../../third_party/closure_compiler/externs/compiled_resources.gyp:passwords_private',
+        ],
+      },
+      'includes': ['../../../../../third_party/closure_compiler/compile_js.gypi'],
+    },
+    {
+      'target_name': 'passwords_section',
+      'includes': ['../../../../../third_party/closure_compiler/compile_js.gypi'],
+      'variables': {
+        'depends': [
+          '../../../../../third_party/closure_compiler/externs/compiled_resources.gyp:passwords_private',
+        ],
+      },
+    },
+  ],
+}
diff --git a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_and_forms_page.js b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_and_forms_page.js
index b46e9fb3..07b6ac1e 100644
--- a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_and_forms_page.js
+++ b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_and_forms_page.js
@@ -27,6 +27,7 @@
     /**
      * An array of passwords to display.
      * Lazy loaded when the password section is expanded.
+     * @type {!Array<!chrome.passwordsPrivate.PasswordUiEntry>}
      */
     savedPasswords: {
       type: Array,
@@ -39,29 +40,16 @@
     passwordsOpened: {
       type: Boolean,
       value: false,
-      observer: 'loadPasswords_',
     },
   },
 
-  /**
-   * Called when the section is expanded. This will load the list of passwords
-   * only when needed.
-   * @param {boolean} passwordSectionOpened
-   */
-  loadPasswords_: function(passwordSectionOpened) {
-    if (passwordSectionOpened) {
-      // TODO(hcarmona): Get real data.
-      this.savedPasswords =
-          [{origin: 'otherwebsite.com',
-            username: 'bowser',
-            password: '************'},
-           {origin: 'otherlongwebsite.com',
-            username: 'koopa',
-            password: '*********'},
-           {origin: 'otherverylongwebsite.com',
-            username: 'goomba',
-            password: '******'}];
-    }
+  /** @override */
+  ready: function() {
+    // Triggers a callback after the listener is added.
+    chrome.passwordsPrivate.onSavedPasswordsListChanged.addListener(
+        function(passwordList) {
+          this.savedPasswords = passwordList;
+        }.bind(this));
   },
 });
 })();
diff --git a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.css b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.css
index a11186f..f9691c1 100644
--- a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.css
+++ b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.css
@@ -25,3 +25,13 @@
   height: 300px;
   padding-top: 16px;
 }
+
+paper-input {
+  --paper-input-container-disabled: {
+    opacity: 1;
+  };
+  --paper-input-container-underline-disabled: {
+    opacity: 0;
+  };
+  width: 150px;
+}
diff --git a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.html b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.html
index 47d9d61..757eaf9 100644
--- a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.html
+++ b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.html
@@ -1,5 +1,6 @@
 <link rel="import" href="chrome://resources/polymer/v1_0/polymer/polymer.html">
 <link rel="import" href="chrome://resources/polymer/v1_0/iron-list/iron-list.html">
+<link rel="import" href="chrome://resources/polymer/v1_0/paper-input/paper-input.html">
 <link rel="import" href="chrome://resources/polymer/v1_0/paper-item/paper-item-body.html">
 <link rel="import" href="chrome://resources/polymer/v1_0/paper-item/paper-item.html">
 
@@ -14,10 +15,14 @@
         <template>
           <paper-item class="separator">
             <paper-item-body two-line>
-              <div id="origin">[[item.origin]]</div>
-              <div id="username"secondary>[[item.username]]</div>
+              <div id="originUrl">[[item.loginPair.originUrl]]</div>
+              <div id="username" secondary>[[item.loginPair.username]]</div>
             </paper-item-body>
-            <div id="password">[[item.password]]</div>
+            <!--TODO(hcarmona): Update password so that it is editable.
+                #password is type password and disabled in order to match UI.-->
+            <paper-input id="password" type="password" disabled
+                value="[[getEmptyPassword_(item.numCharactersInPassword)]]">
+            </paper-input>
           </paper-item>
         </template>
       </iron-list>
diff --git a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.js b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.js
index fc506e8..4eb338d8 100644
--- a/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.js
+++ b/chrome/browser/resources/settings/passwords_and_forms_page/passwords_section.js
@@ -19,11 +19,20 @@
   properties: {
     /**
      * An array of passwords to display.
+     * @type {!Array<!chrome.passwordsPrivate.PasswordUiEntry>}
      */
     savedPasswords: {
       type: Array,
       value: function() { return []; },
     },
   },
+
+  /**
+   * Creates an empty password of specified length.
+   * @param {number} length
+   * @return {string} password
+   * @private
+   */
+  getEmptyPassword_(length) { return ' '.repeat(length); },
 });
 })();
diff --git a/chrome/chrome_common.gypi b/chrome/chrome_common.gypi
index 75a8e2a..3941486 100644
--- a/chrome/chrome_common.gypi
+++ b/chrome/chrome_common.gypi
@@ -317,7 +317,6 @@
         'safe_browsing_proto',
         '<(DEPTH)/base/base.gyp:base',
         '<(DEPTH)/base/base.gyp:base_i18n',
-        '<(DEPTH)/base/base.gyp:base_prefs',
         '<(DEPTH)/base/base.gyp:base_static',
         '<(DEPTH)/chrome/chrome_features.gyp:chrome_common_features',
         '<(DEPTH)/chrome/chrome_resources.gyp:chrome_resources',
@@ -342,6 +341,7 @@
         '<(DEPTH)/components/components.gyp:variations',
         '<(DEPTH)/components/components.gyp:version_info',
         '<(DEPTH)/components/components_strings.gyp:components_strings',
+        '<(DEPTH)/components/prefs/prefs.gyp:prefs',
         '<(DEPTH)/components/url_formatter/url_formatter.gyp:url_formatter',
         '<(DEPTH)/content/content.gyp:content_common',
         '<(DEPTH)/crypto/crypto.gyp:crypto',
diff --git a/chrome/chrome_tests_unit.gypi b/chrome/chrome_tests_unit.gypi
index d0e2f5d..ec1344f 100644
--- a/chrome/chrome_tests_unit.gypi
+++ b/chrome/chrome_tests_unit.gypi
@@ -1677,7 +1677,6 @@
         'chrome_resources.gyp:chrome_strings',
         'chrome_resources.gyp:theme_resources',
         'common',
-        '../base/base.gyp:base_prefs_test_support',
         '../base/base.gyp:test_support_base',
         '../components/components.gyp:bookmarks_test_support',
         '../components/components.gyp:browser_sync_browser_test_support',
@@ -1700,6 +1699,7 @@
         '../components/components.gyp:toolbar_test_support',
         '../components/components.gyp:update_client_test_support',
         '../components/components.gyp:user_prefs_tracked_test_support',
+        '../components/prefs/prefs.gyp:prefs_test_support',
         '../content/content.gyp:content_app_both',
         '../content/content_shell_and_tests.gyp:test_support_content',
         '../net/net.gyp:net',
diff --git a/chrome/common/BUILD.gn b/chrome/common/BUILD.gn
index fb57a95..b9b45487 100644
--- a/chrome/common/BUILD.gn
+++ b/chrome/common/BUILD.gn
@@ -62,7 +62,6 @@
     "//base:base",
     "//base:base_static",
     "//base:i18n",
-    "//base:prefs",
     "//chrome:resources",
     "//chrome:strings",
     "//chrome/app/theme:theme_resources",
@@ -88,6 +87,7 @@
     "//components/offline_pages:switches",
     "//components/omnibox/common",
     "//components/policy:policy_component_common",
+    "//components/prefs",
     "//components/strings",
     "//components/translate/core/common",
     "//components/url_formatter",
diff --git a/chrome/test/BUILD.gn b/chrome/test/BUILD.gn
index 7ff1c1c7..ea7f8c9 100644
--- a/chrome/test/BUILD.gn
+++ b/chrome/test/BUILD.gn
@@ -84,7 +84,6 @@
 
   # New deps should go in the non-iOS section below.
   public_deps = [
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//chrome:resources",
     "//chrome:strings",
@@ -102,6 +101,7 @@
     "//components/omnibox/browser:test_support",
     "//components/password_manager/core/browser:test_support",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//components/rappor:test_support",
     "//components/search_engines:test_support",
     "//components/signin/core/browser:test_support",
diff --git a/chrome/test/data/webui/settings/settings_passwords_section_browsertest.js b/chrome/test/data/webui/settings/settings_passwords_section_browsertest.js
index c6467b2..67b36ba0 100644
--- a/chrome/test/data/webui/settings/settings_passwords_section_browsertest.js
+++ b/chrome/test/data/webui/settings/settings_passwords_section_browsertest.js
@@ -26,6 +26,55 @@
 
   /** @override */
   extraLibraries: PolymerTest.getLibraries(ROOT_PATH),
+
+  /** @override */
+  setUp: function() {
+    PolymerTest.prototype.setUp.call(this);
+
+    // Test is run on an individual element that won't have a page language.
+    this.accessibilityAuditConfig.auditRulesToIgnore.push('humanLangMissing');
+  },
+
+  /**
+   * Creates a single item for the list of passwords.
+   * @param {string} url
+   * @param {string} username
+   * @param {number} passwordLength
+   * @return {chrome.passwordsPrivate.PasswordUiEntry}
+   * @private
+   */
+  createPasswordItem_: function(url, username, passwordLength) {
+    return {
+      loginPair: {originUrl: url, username: username},
+      numCharactersInPassword: passwordLength
+    };
+  },
+
+  /**
+   * Helper method that validates a node matches the data for an index.
+   * @param {!Array<!Element>} nodes The nodes that will be checked.
+   * @param {!Array<!Object>} passwordList The expected data.
+   * @param {number} index The index that should match the node and data.
+   * @private
+   */
+  validate_: function(nodes, passwordList, index) {
+    var node = nodes[index];
+    var passwordInfo = passwordList[index];
+    assertTrue(!!node, 'Failed to get nodes[' + index + ']');
+    assertTrue(!!passwordInfo, 'Failed to get passwordList[' + index + ']');
+    assertEquals(
+        passwordInfo.loginPair.originUrl,
+        node.querySelector('#originUrl').textContent,
+        'originUrl mismatch in nodes[' + index + ']');
+    assertEquals(
+        passwordInfo.loginPair.username,
+        node.querySelector('#username').textContent,
+        'username mismatch in nodes[' + index + ']');
+    assertEquals(
+        passwordInfo.numCharactersInPassword,
+        node.querySelector('#password').value.length,
+        'password size mismatch in nodes[' + index + ']');
+  },
 };
 
 /**
@@ -39,15 +88,11 @@
       assertEquals(self.browsePreload, document.location.href,
                    'Unexpected URL loaded');
 
-      var passwordList = [{origin: 'anotherwebsite.com',
-                           username: 'luigi',
-                           password: '*******'},
-                          {origin: 'longwebsite.com',
-                           username: 'peach',
-                           password: '***'},
-                          {origin: 'website.com',
-                           username: 'mario',
-                           password: '*******'}];
+      var passwordList = [
+        self.createPasswordItem_('anotherwebsite.com', 'luigi', 1),
+        self.createPasswordItem_('longwebsite.com', 'peach', 7),
+        self.createPasswordItem_('website.com', 'mario', 70)
+      ];
 
       // Create a passwords-section to use for testing.
       var passwordsSection = document.createElement('passwords-section');
@@ -62,26 +107,13 @@
                      'Failed to pass list of passwords to iron-list');
 
         var list = Polymer.dom(passwordsSection.$.passwordList);
-        assertTrue(!!list, "Failed to get the password list");
+        assertTrue(!!list, 'Failed to get the password list');
         // Skip the first child because it's the template.
         var listChildren = list.children.slice(1);
 
-        var validate = function(nodes, passwordList, index) {
-          assertTrue(!!nodes[index], 'Failed to get nodes[' + index + ']');
-          assertEquals(passwordList[index].origin,
-                       nodes[index].querySelector('#origin').textContent,
-                       'origin mismatch in nodes[' + index + ']');
-          assertEquals(passwordList[index].username,
-                       nodes[index].querySelector('#username').textContent,
-                       'username mismatch in nodes[' + index + ']');
-          assertEquals(passwordList[index].password,
-                       nodes[index].querySelector('#password').textContent,
-                       'password mismatch in nodes[' + index + ']');
-        };
-
-        validate(listChildren, passwordList, 0);
-        validate(listChildren, passwordList, 1);
-        validate(listChildren, passwordList, 2);
+        self.validate_(listChildren, passwordList, 0);
+        self.validate_(listChildren, passwordList, 1);
+        self.validate_(listChildren, passwordList, 2);
         done();
       }, 0);
     });
diff --git a/chromecast/browser/BUILD.gn b/chromecast/browser/BUILD.gn
index afae1de..f187fe33 100644
--- a/chromecast/browser/BUILD.gn
+++ b/chromecast/browser/BUILD.gn
@@ -76,7 +76,6 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//cc",
     "//chromecast/app:cast_crash_client",
     "//chromecast/app:chromecast_settings",
@@ -100,6 +99,7 @@
     # isn't needed. crbug.com/541577
     "//components/metrics:ui",
     "//components/network_hints/browser",
+    "//components/prefs",
     "//content",
     "//content/public/browser",
     "//content/public/common",
diff --git a/chromecast/browser/metrics/BUILD.gn b/chromecast/browser/metrics/BUILD.gn
index fad608a3..ef66b24 100644
--- a/chromecast/browser/metrics/BUILD.gn
+++ b/chromecast/browser/metrics/BUILD.gn
@@ -15,13 +15,13 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//chromecast/base",
     "//chromecast/common",
     "//components/metrics",
     "//components/metrics:gpu",
     "//components/metrics:net",
     "//components/metrics:profiler",
+    "//components/prefs",
     "//content/public/browser",
     "//content/public/common",
   ]
diff --git a/chromeos/BUILD.gn b/chromeos/BUILD.gn
index 3cecead..8ab2c15 100644
--- a/chromeos/BUILD.gn
+++ b/chromeos/BUILD.gn
@@ -28,11 +28,11 @@
     ":power_manager_proto",
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//base/third_party/dynamic_annotations",
     "//components/device_event_log",
     "//components/onc",
     "//components/policy/proto",
+    "//components/prefs",
     "//components/proxy_config",
     "//components/signin/core/account_id",
     "//crypto",
@@ -144,10 +144,10 @@
     ":cryptohome_proto",
     ":power_manager_proto",
     ":test_support",
-    "//base:prefs_test_support",
     "//base/test:run_all_unittests",
     "//base/test:test_support",
     "//components/onc",
+    "//components/prefs:test_support",
     "//components/proxy_config",
     "//crypto",
     "//crypto:test_support",
diff --git a/chromeos/CHROMEOS_LKGM b/chromeos/CHROMEOS_LKGM
index 559c263..23c0246d 100644
--- a/chromeos/CHROMEOS_LKGM
+++ b/chromeos/CHROMEOS_LKGM
@@ -1 +1 @@
-7873.0.0
\ No newline at end of file
+7876.0.0
\ No newline at end of file
diff --git a/chromeos/chromeos.gyp b/chromeos/chromeos.gyp
index 2aeeec8..c0f9ab53 100644
--- a/chromeos/chromeos.gyp
+++ b/chromeos/chromeos.gyp
@@ -511,7 +511,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
         '../build/linux/system.gyp:dbus',
         '../build/linux/system.gyp:ssl',
@@ -520,6 +519,7 @@
         '../components/components.gyp:onc_component',
         '../components/components.gyp:proxy_config',
         '../components/components.gyp:signin_core_account_id',
+        '../components/prefs/prefs.gyp:prefs',
         '../crypto/crypto.gyp:crypto',
         '../dbus/dbus.gyp:dbus',
         '../google_apis/google_apis.gyp:google_apis',
@@ -644,13 +644,13 @@
       'target_name': 'chromeos_unittests',
       'type': 'executable',
       'dependencies': [
-        '../base/base.gyp:base_prefs_test_support',
         '../base/base.gyp:run_all_unittests',
         '../base/base.gyp:test_support_base',
         '../build/linux/system.gyp:dbus',
         '../build/linux/system.gyp:ssl',
         '../components/components.gyp:onc_component',
         '../components/components.gyp:proxy_config',
+        '../components/prefs/prefs.gyp:prefs_test_support',
         '../crypto/crypto.gyp:crypto',
         '../crypto/crypto.gyp:crypto_test_support',
         '../dbus/dbus.gyp:dbus_test_support',
diff --git a/components/BUILD.gn b/components/BUILD.gn
index ad3fab2..9841da3 100644
--- a/components/BUILD.gn
+++ b/components/BUILD.gn
@@ -63,6 +63,7 @@
     "//components/network_time:unit_tests",
     "//components/open_from_clipboard:unit_tests",
     "//components/os_crypt:unit_tests",
+    "//components/prefs:unit_tests",
     "//components/proxy_config:unit_tests",
     "//components/security_state:unit_tests",
     "//components/sessions:unit_tests",
@@ -418,9 +419,9 @@
     # a MANUAL component_browsertest.
     sources += [ "dom_distiller/standalone/content_extractor_browsertest.cc" ]
     deps += [
-      "//base:prefs_test_support",
       "//components/leveldb_proto",
       "//components/pref_registry:test_support",
+      "//components/prefs:test_support",
     ]
   }
 
diff --git a/components/arc/BUILD.gn b/components/arc/BUILD.gn
index eb8320b..3b09082 100644
--- a/components/arc/BUILD.gn
+++ b/components/arc/BUILD.gn
@@ -35,10 +35,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//chromeos",
     "//chromeos:power_manager_proto",
     "//components/onc",
+    "//components/prefs",
     "//components/signin/core/account_id",
     "//google_apis",
     "//ipc:ipc",
diff --git a/components/autofill.gypi b/components/autofill.gypi
index 93d634f..ca9e8e0 100644
--- a/components/autofill.gypi
+++ b/components/autofill.gypi
@@ -65,7 +65,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../google_apis/google_apis.gyp:google_apis',
         '../net/net.gyp:net',
         '../skia/skia.gyp:skia',
@@ -91,6 +90,7 @@
         'keyed_service_core',
         'os_crypt',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
         'rappor',
         'signin_core_browser',
         'signin_core_common',
@@ -277,7 +277,6 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../base/base.gyp:test_support_base',
         '../skia/skia.gyp:skia',
         '../testing/gtest.gyp:gtest',
@@ -285,6 +284,7 @@
         'autofill_core_browser',
         'os_crypt',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
         'rappor',
         'signin_core_browser_test_support',
       ],
@@ -380,7 +380,6 @@
           'dependencies': [
             '../base/base.gyp:base',
             '../base/base.gyp:base_i18n',
-            '../base/base.gyp:base_prefs',
             '../content/content.gyp:content_browser',
             '../content/content.gyp:content_common',
             '../google_apis/google_apis.gyp:google_apis',
@@ -403,6 +402,7 @@
             'components_resources.gyp:components_resources',
             'components_strings.gyp:components_strings',
             'os_crypt',
+            'prefs/prefs.gyp:prefs',
             'user_prefs',
             'webdata_common',
           ],
diff --git a/components/autofill/content/browser/BUILD.gn b/components/autofill/content/browser/BUILD.gn
index d67c309..baa997d6 100644
--- a/components/autofill/content/browser/BUILD.gn
+++ b/components/autofill/content/browser/BUILD.gn
@@ -32,10 +32,10 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/autofill/content/common",
     "//components/autofill/core/browser",
     "//components/autofill/core/common",
+    "//components/prefs",
     "//components/os_crypt",
     "//components/resources",
     "//components/strings",
diff --git a/components/autofill/core/browser/BUILD.gn b/components/autofill/core/browser/BUILD.gn
index 95a0cbf..b0008d4 100644
--- a/components/autofill/core/browser/BUILD.gn
+++ b/components/autofill/core/browser/BUILD.gn
@@ -167,7 +167,6 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/autofill/core/browser/proto",
     "//components/autofill/core/common",
     "//components/data_use_measurement/core",
@@ -175,6 +174,7 @@
     "//components/keyed_service/core",
     "//components/os_crypt",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/rappor",
     "//components/resources",
     "//components/signin/core/browser",
@@ -233,14 +233,13 @@
 
   deps = [
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/autofill/core/browser",
     "//components/autofill/core/browser/proto",
     "//components/autofill/core/common",
     "//components/os_crypt",
     "//components/pref_registry",
+    "//components/prefs:test_support",
     "//components/rappor",
     "//components/rappor:test_support",
     "//components/signin/core/browser",
@@ -298,11 +297,10 @@
     ":browser",
     ":test_support",
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/autofill/core/common",
     "//components/os_crypt",
+    "//components/prefs:test_support",
     "//components/rappor:test_support",
     "//components/resources",
     "//components/signin/core/browser",
diff --git a/components/bookmarks/browser/BUILD.gn b/components/bookmarks/browser/BUILD.gn
index c0ec3b2..24e1721f 100644
--- a/components/bookmarks/browser/BUILD.gn
+++ b/components/bookmarks/browser/BUILD.gn
@@ -44,11 +44,11 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/bookmarks/common",
     "//components/favicon_base",
     "//components/keyed_service/core",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/query_parser",
     "//components/strings",
     "//components/url_formatter",
@@ -83,12 +83,12 @@
 
   deps = [
     ":browser",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//components/bookmarks/common",
     "//components/bookmarks/test",
     "//components/favicon_base",
     "//components/pref_registry",
+    "//components/prefs",
+    "//components/prefs:test_support",
     "//testing/gtest",
     "//ui/base",
     "//url",
diff --git a/components/bookmarks/managed/BUILD.gn b/components/bookmarks/managed/BUILD.gn
index ed8d2a6..f2f2765 100644
--- a/components/bookmarks/managed/BUILD.gn
+++ b/components/bookmarks/managed/BUILD.gn
@@ -14,10 +14,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/bookmarks/browser",
     "//components/bookmarks/common",
     "//components/keyed_service/core",
+    "//components/prefs",
     "//components/strings",
     "//ui/base",
     "//url",
@@ -35,11 +35,10 @@
   deps = [
     ":managed",
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//components/bookmarks/browser",
     "//components/bookmarks/common",
     "//components/bookmarks/test",
+    "//components/prefs:test_support",
     "//components/strings",
     "//testing/gmock",
     "//testing/gtest",
diff --git a/components/browser_sync/browser/BUILD.gn b/components/browser_sync/browser/BUILD.gn
index c7592a6..a80bb84 100644
--- a/components/browser_sync/browser/BUILD.gn
+++ b/components/browser_sync/browser/BUILD.gn
@@ -16,7 +16,6 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/autofill/core/browser",
     "//components/autofill/core/common",
     "//components/browser_sync/common",
@@ -28,6 +27,7 @@
     "//components/password_manager/core/browser",
     "//components/password_manager/sync/browser",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/signin/core/browser",
     "//components/strings",
     "//components/sync_bookmarks",
diff --git a/components/components_tests.gyp b/components/components_tests.gyp
index e004816..22e2568 100644
--- a/components/components_tests.gyp
+++ b/components/components_tests.gyp
@@ -586,6 +586,18 @@
       'proxy_config/proxy_config_dictionary_unittest.cc',
       'proxy_config/proxy_prefs_unittest.cc',
     ],
+    'prefs_unittest_sources': [
+      'prefs/default_pref_store_unittest.cc',
+      'prefs/json_pref_store_unittest.cc',
+      'prefs/overlay_user_pref_store_unittest.cc',
+      'prefs/pref_change_registrar_unittest.cc',
+      'prefs/pref_member_unittest.cc',
+      'prefs/pref_notifier_impl_unittest.cc',
+      'prefs/pref_service_unittest.cc',
+      'prefs/pref_value_map_unittest.cc',
+      'prefs/pref_value_store_unittest.cc',
+      'prefs/scoped_user_pref_update_unittest.cc',
+    ],
     'query_parser_unittest_sources': [
       'query_parser/query_parser_unittest.cc',
       'query_parser/snippet_unittest.cc',
@@ -939,6 +951,7 @@
         '<@(password_manager_unittest_sources)',
         '<@(precache_unittest_sources)',
         '<@(proxy_config_unittest_sources)',
+        '<@(prefs_unittest_sources)',
         '<@(query_parser_unittest_sources)',
         '<@(rappor_unittest_sources)',
         '<@(search_engines_unittest_sources)',
@@ -971,7 +984,6 @@
       ],
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs_test_support',
         '../base/base.gyp:test_support_base',
         '../google_apis/google_apis.gyp:google_apis_test_support',
         '../jingle/jingle.gyp:notifier_test_util',
@@ -1106,6 +1118,8 @@
         'components_strings.gyp:components_strings',
         'components_tests_pak',
         'mime_util/mime_util.gyp:mime_util',
+        'prefs/prefs.gyp:prefs',
+        'prefs/prefs.gyp:prefs_test_support',
         'url_formatter/url_formatter.gyp:url_formatter',
       ],
       'conditions': [
diff --git a/components/content_settings.gypi b/components/content_settings.gypi
index fdca4ba..c547bad 100644
--- a/components/content_settings.gypi
+++ b/components/content_settings.gypi
@@ -10,11 +10,11 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../net/net.gyp:net',
         '../url/url.gyp:url_lib',
         'content_settings_core_common',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
         'url_formatter/url_formatter.gyp:url_formatter',
       ],
       'variables': { 'enable_wexit_time_destructors': 1, },
diff --git a/components/content_settings/core/browser/BUILD.gn b/components/content_settings/core/browser/BUILD.gn
index 6cf81ef..013fe88 100644
--- a/components/content_settings/core/browser/BUILD.gn
+++ b/components/content_settings/core/browser/BUILD.gn
@@ -55,10 +55,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/content_settings/core/common",
     "//components/keyed_service/core",
     "//components/pref_registry:pref_registry",
+    "//components/prefs",
     "//components/url_formatter",
     "//net",
     "//url",
@@ -86,11 +86,11 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs",
     "//base/test:test_support",
     "//components/content_settings/core/common",
     "//components/content_settings/core/test:test_support",
     "//components/pref_registry:test_support",
+    "//components/prefs",
     "//testing/gtest",
     "//url",
   ]
diff --git a/components/cronet/android/BUILD.gn b/components/cronet/android/BUILD.gn
index ed917a7..b6102e4 100644
--- a/components/cronet/android/BUILD.gn
+++ b/components/cronet/android/BUILD.gn
@@ -107,9 +107,9 @@
       ":features",
       "//base",
       "//base:i18n",
-      "//base:prefs",
       "//base/third_party/dynamic_annotations",
       "//components/metrics",
+      "//components/prefs",
     ]
     sources = [
       "//components/cronet/android/chromium_url_request.cc",
diff --git a/components/data_reduction_proxy/core/browser/BUILD.gn b/components/data_reduction_proxy/core/browser/BUILD.gn
index 69f3344..77ef2a4 100644
--- a/components/data_reduction_proxy/core/browser/BUILD.gn
+++ b/components/data_reduction_proxy/core/browser/BUILD.gn
@@ -57,10 +57,10 @@
 
     deps = [
       "//base",
-      "//base:prefs",
       "//components/data_reduction_proxy/core/common:common_small",
       "//components/data_reduction_proxy/proto:data_reduction_proxy_proto",
       "//components/pref_registry",
+      "//components/prefs",
       "//components/variations",
       "//crypto",
       "//google_apis:google_apis_small",
@@ -79,10 +79,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/data_reduction_proxy/core/common",
     "//components/data_reduction_proxy/proto:data_reduction_proxy_proto",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/variations",
     "//crypto",
     "//google_apis",
@@ -117,9 +117,9 @@
   ]
   deps = [
     "//base",
-    "//base:prefs_test_support",
     "//components/data_reduction_proxy/core/common",
     "//components/data_reduction_proxy/core/common:test_support",
+    "//components/prefs:test_support",
     "//net",
     "//net:test_support",
     "//testing/gmock",
@@ -156,10 +156,10 @@
     ":browser",
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/data_reduction_proxy/core/common:test_support",
     "//components/data_reduction_proxy/proto:data_reduction_proxy_proto",
+    "//components/prefs:test_support",
     "//components/variations",
     "//net:test_support",
     "//testing/gmock",
diff --git a/components/dom_distiller.gypi b/components/dom_distiller.gypi
index 9b74614..51562693 100644
--- a/components/dom_distiller.gypi
+++ b/components/dom_distiller.gypi
@@ -54,7 +54,6 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../skia/skia.gyp:skia',
         '../sync/sync.gyp:sync',
         '../third_party/dom_distiller_js/dom_distiller_js.gyp:dom_distiller_js_proto',
@@ -63,6 +62,7 @@
         'components_resources.gyp:components_resources',
         'components_strings.gyp:components_strings',
         'dom_distiller_protos',
+        'prefs/prefs.gyp:prefs',
         'pref_registry',
         'variations',
       ],
diff --git a/components/dom_distiller/core/BUILD.gn b/components/dom_distiller/core/BUILD.gn
index b3e6486..7c6dbb6 100644
--- a/components/dom_distiller/core/BUILD.gn
+++ b/components/dom_distiller/core/BUILD.gn
@@ -64,9 +64,9 @@
   ]
   deps = [
     "//base",
-    "//base:prefs",
     "//components/leveldb_proto",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/resources",
     "//components/strings",
     "//components/variations",
diff --git a/components/domain_reliability.gypi b/components/domain_reliability.gypi
index eae16ab..3a6155a 100644
--- a/components/domain_reliability.gypi
+++ b/components/domain_reliability.gypi
@@ -13,9 +13,9 @@
       'type': '<(component)',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../components/components.gyp:data_use_measurement_core',
         '../components/components.gyp:keyed_service_core',
+        '../components/prefs/prefs.gyp:prefs',
         '../content/content.gyp:content_browser',
         '../net/net.gyp:net',
         '../url/url.gyp:url_lib',
diff --git a/components/drive/BUILD.gn b/components/drive/BUILD.gn
index 273027f..806e4023 100644
--- a/components/drive/BUILD.gn
+++ b/components/drive/BUILD.gn
@@ -50,9 +50,9 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/invalidation/public",
     "//components/keyed_service/core",
+    "//components/prefs",
 
     # TODO(lukasza): Remove this dependency (see DEPS file for more info).
     "//content/public/browser",
@@ -129,7 +129,7 @@
     ":drive",
     "//base",
     "//base:i18n",
-    "//base:prefs",
+    "//components/prefs",
     "//google_apis:google_apis",
     "//net:net",
   ]
@@ -158,7 +158,7 @@
     ":drive",
     ":proto",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//content/test:test_support",
     "//google_apis:test_support",
     "//net:net",
@@ -182,7 +182,7 @@
     ":drive_chromeos",
     ":proto",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//content/test:test_support",
     "//google_apis:test_support",
   ]
diff --git a/components/feedback/BUILD.gn b/components/feedback/BUILD.gn
index ec4e9f19..0a017a01 100644
--- a/components/feedback/BUILD.gn
+++ b/components/feedback/BUILD.gn
@@ -54,10 +54,10 @@
   deps = [
     ":feedback",
     "//base",
-    "//base:prefs_test_support",
     "//components/feedback/proto",
     "//components/keyed_service/core",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//components/user_prefs",
     "//components/variations/net",
     "//content/test:test_support",
diff --git a/components/filesystem/public/cpp/prefs/BUILD.gn b/components/filesystem/public/cpp/prefs/BUILD.gn
index 22131db..2300ab6e 100644
--- a/components/filesystem/public/cpp/prefs/BUILD.gn
+++ b/components/filesystem/public/cpp/prefs/BUILD.gn
@@ -12,8 +12,8 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/filesystem/public/interfaces",
+    "//components/prefs",
     "//mojo/common",
     "//mojo/shell/public/cpp",
   ]
diff --git a/components/flags_ui.gypi b/components/flags_ui.gypi
index f4c6275..31e3653 100644
--- a/components/flags_ui.gypi
+++ b/components/flags_ui.gypi
@@ -13,8 +13,8 @@
       ],
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../components/components_strings.gyp:components_strings',
+        '../components/prefs/prefs.gyp:prefs',
         '../ui/base/ui_base.gyp:ui_base',
         'flags_ui_switches',
         'pref_registry',
diff --git a/components/flags_ui/BUILD.gn b/components/flags_ui/BUILD.gn
index 8669902..81f0f5c1 100644
--- a/components/flags_ui/BUILD.gn
+++ b/components/flags_ui/BUILD.gn
@@ -21,8 +21,8 @@
   deps = [
     ":switches",
     "//base",
-    "//base:prefs",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/strings",
     "//ui/base",
   ]
@@ -47,8 +47,7 @@
     ":flags_ui",
     ":switches",
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//components/strings",
     "//testing/gtest",
   ]
diff --git a/components/gcm_driver/BUILD.gn b/components/gcm_driver/BUILD.gn
index d02948b7..d83be21 100644
--- a/components/gcm_driver/BUILD.gn
+++ b/components/gcm_driver/BUILD.gn
@@ -61,12 +61,12 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/gcm_driver/common",
     "//components/gcm_driver/crypto",
     "//components/keyed_service/core",
     "//components/os_crypt",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/signin/core/browser",
     "//components/sync_driver",
     "//components/version_info",
@@ -159,8 +159,8 @@
     ":gcm_driver",
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//google_apis:test_support",
     "//google_apis/gcm:test_support",
     "//net:test_support",
diff --git a/components/google/core/browser/BUILD.gn b/components/google/core/browser/BUILD.gn
index d98d61b..ad600616 100644
--- a/components/google/core/browser/BUILD.gn
+++ b/components/google/core/browser/BUILD.gn
@@ -18,10 +18,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/data_use_measurement/core",
     "//components/keyed_service/core",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/strings",
     "//components/url_formatter",
     "//net",
@@ -40,8 +40,7 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//net:test_support",
     "//testing/gtest",
   ]
diff --git a/components/history.gypi b/components/history.gypi
index a8c5091..20f647c 100644
--- a/components/history.gypi
+++ b/components/history.gypi
@@ -14,7 +14,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../google_apis/google_apis.gyp:google_apis',
         '../net/net.gyp:net',
         '../skia/skia.gyp:skia',
@@ -27,6 +26,7 @@
         'favicon_base',
         'history_core_common',
         'keyed_service_core',
+        'prefs/prefs.gyp:prefs',
         'query_parser',
         'signin_core_browser',
         'sync_driver',
diff --git a/components/history/core/browser/BUILD.gn b/components/history/core/browser/BUILD.gn
index 0d88839..3d038fd0 100644
--- a/components/history/core/browser/BUILD.gn
+++ b/components/history/core/browser/BUILD.gn
@@ -93,10 +93,10 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/favicon_base",
     "//components/history/core/common",
     "//components/keyed_service/core",
+    "//components/prefs",
     "//components/query_parser",
     "//components/signin/core/browser",
     "//components/sync_driver",
@@ -160,11 +160,11 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/favicon_base",
     "//components/history/core/common",
     "//components/history/core/test",
+    "//components/prefs:test_support",
     "//components/sync_driver:test_support",
     "//sql",
     "//sql:test_support",
diff --git a/components/invalidation.gypi b/components/invalidation.gypi
index 662a077..0ab96ae 100644
--- a/components/invalidation.gypi
+++ b/components/invalidation.gypi
@@ -50,7 +50,6 @@
         'invalidation_public',
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../google_apis/google_apis.gyp:google_apis',
         '../jingle/jingle.gyp:notifier',
         '../third_party/cacheinvalidation/cacheinvalidation.gyp:cacheinvalidation_proto_cpp',
@@ -58,6 +57,7 @@
         'gcm_driver',
         'keyed_service_core',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
         'signin_core_browser',
       ],
       'export_dependent_settings': [
diff --git a/components/invalidation/impl/BUILD.gn b/components/invalidation/impl/BUILD.gn
index a363dcb9..bbbd4f2 100644
--- a/components/invalidation/impl/BUILD.gn
+++ b/components/invalidation/impl/BUILD.gn
@@ -39,11 +39,11 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/data_use_measurement/core",
     "//components/gcm_driver",
     "//components/keyed_service/core",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/signin/core/browser",
     "//google_apis",
     "//jingle:notifier",
@@ -107,7 +107,7 @@
     ":impl",
     ":test_support",
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//testing/gmock",
     "//testing/gtest",
   ]
diff --git a/components/keyed_service.gypi b/components/keyed_service.gypi
index 26bfc05..5bfef70 100644
--- a/components/keyed_service.gypi
+++ b/components/keyed_service.gypi
@@ -18,7 +18,7 @@
       'msvs_disabled_warnings': [ 4267, ],
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
+        'prefs/prefs.gyp:prefs',
         'user_prefs',
       ],
       'sources': [
diff --git a/components/keyed_service/core/BUILD.gn b/components/keyed_service/core/BUILD.gn
index 3ba7a45..79a0ed3 100644
--- a/components/keyed_service/core/BUILD.gn
+++ b/components/keyed_service/core/BUILD.gn
@@ -31,8 +31,8 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/user_prefs",
   ]
 }
diff --git a/components/metrics.gypi b/components/metrics.gypi
index 643c9df..b90ebc6 100644
--- a/components/metrics.gypi
+++ b/components/metrics.gypi
@@ -14,9 +14,9 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../third_party/zlib/google/zip.gyp:compression_utils',
         'component_metrics_proto',
+        'prefs/prefs.gyp:prefs',
         'variations',
       ],
       'export_dependent_settings': [
diff --git a/components/metrics/BUILD.gn b/components/metrics/BUILD.gn
index f75a3f9..13701ba 100644
--- a/components/metrics/BUILD.gn
+++ b/components/metrics/BUILD.gn
@@ -66,7 +66,7 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
+    "//components/prefs",
     "//components/variations",
     "//third_party/zlib:compression_utils",
   ]
@@ -322,8 +322,8 @@
     ":profiler",
     ":test_support",
     ":ui",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//components/variations",
     "//net:test_support",
     "//testing/gtest",
diff --git a/components/network_time/BUILD.gn b/components/network_time/BUILD.gn
index be9b44cf..14057f9 100644
--- a/components/network_time/BUILD.gn
+++ b/components/network_time/BUILD.gn
@@ -13,7 +13,7 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
+    "//components/prefs",
   ]
 }
 
@@ -26,7 +26,7 @@
   deps = [
     ":network_time",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//testing/gtest",
   ]
 }
diff --git a/components/omnibox/browser/BUILD.gn b/components/omnibox/browser/BUILD.gn
index 703e5aa..329a1af 100644
--- a/components/omnibox/browser/BUILD.gn
+++ b/components/omnibox/browser/BUILD.gn
@@ -110,7 +110,6 @@
     ":in_memory_url_index_cache_proto",
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/bookmarks/browser",
     "//components/data_use_measurement/core",
     "//components/keyed_service/core",
@@ -118,6 +117,7 @@
     "//components/omnibox/common",
     "//components/open_from_clipboard",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/query_parser",
     "//components/resources",
     "//components/search",
@@ -205,13 +205,12 @@
     ":browser",
     ":test_support",
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/bookmarks/browser",
     "//components/bookmarks/test",
     "//components/history/core/test",
     "//components/open_from_clipboard:test_support",
+    "//components/prefs:test_support",
     "//components/search",
     "//components/search_engines",
     "//components/url_formatter",
diff --git a/components/password_manager/content/browser/BUILD.gn b/components/password_manager/content/browser/BUILD.gn
index c759643..85f89dc0 100644
--- a/components/password_manager/content/browser/BUILD.gn
+++ b/components/password_manager/content/browser/BUILD.gn
@@ -18,7 +18,6 @@
 
   public_deps = [
     "//base",
-    "//base:prefs",
     "//components/autofill/content/browser",
     "//components/autofill/content/common",
     "//components/autofill/core/common",
@@ -26,6 +25,7 @@
     "//components/password_manager/content/common",
     "//components/password_manager/core/browser",
     "//components/password_manager/core/common",
+    "//components/prefs",
     "//content/public/browser",
     "//content/public/common",
     "//ipc",
@@ -41,9 +41,9 @@
   ]
   deps = [
     ":browser",
-    "//base:prefs_test_support",
     "//components/autofill/core/browser:test_support",
     "//components/password_manager/core/browser:test_support",
+    "//components/prefs:test_support",
     "//content/test:test_support",
     "//testing/gmock",
     "//testing/gtest",
diff --git a/components/password_manager/core/browser/BUILD.gn b/components/password_manager/core/browser/BUILD.gn
index 0fc0340b..fea92bc 100644
--- a/components/password_manager/core/browser/BUILD.gn
+++ b/components/password_manager/core/browser/BUILD.gn
@@ -115,13 +115,13 @@
     ":proto",
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/autofill/core/browser",
     "//components/autofill/core/common",
     "//components/keyed_service/core",
     "//components/os_crypt",
     "//components/password_manager/core/common",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/strings",
     "//components/sync_driver",
     "//components/url_formatter",
@@ -224,13 +224,13 @@
   ]
   deps = [
     ":test_support",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/autofill/core/browser:test_support",
     "//components/autofill/core/common",
     "//components/os_crypt",
     "//components/password_manager/core/browser:proto",
     "//components/password_manager/core/common",
+    "//components/prefs:test_support",
     "//components/strings",
     "//components/sync_driver:test_support",
     "//components/variations",
diff --git a/components/password_manager/sync/browser/BUILD.gn b/components/password_manager/sync/browser/BUILD.gn
index cfbd5b1..6aacc17 100644
--- a/components/password_manager/sync/browser/BUILD.gn
+++ b/components/password_manager/sync/browser/BUILD.gn
@@ -18,11 +18,11 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/autofill/core/common",
     "//components/keyed_service/core",
     "//components/password_manager/core/browser",
     "//components/password_manager/core/common",
+    "//components/prefs",
     "//components/signin/core/browser",
     "//components/sync_driver",
     "//components/syncable_prefs",
@@ -44,12 +44,12 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs",
     "//base/test:test_support",
     "//components/autofill/core/common",
     "//components/password_manager/core/browser:test_support",
     "//components/password_manager/core/common",
     "//components/pref_registry:test_support",
+    "//components/prefs",
     "//components/signin/core/browser:test_support",
     "//components/signin/core/common",
     "//components/sync_driver:test_support",
diff --git a/components/policy/core/browser/BUILD.gn b/components/policy/core/browser/BUILD.gn
index 05c61a5..ff65ce41 100644
--- a/components/policy/core/browser/BUILD.gn
+++ b/components/policy/core/browser/BUILD.gn
@@ -19,12 +19,12 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//base/third_party/dynamic_annotations",
     "//components/bookmarks/managed",
     "//components/keyed_service/core",
     "//components/policy/core/common",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/strings",
     "//components/url_matcher",
     "//ui/base",
@@ -96,10 +96,10 @@
     ]
     deps = [
       "//base",
-      "//base:prefs_test_support",
       "//components/autofill/core/common",
       "//components/policy",
       "//components/policy:policy_component_test_support",
+      "//components/prefs:test_support",
       "//components/proxy_config",
       "//components/url_formatter",
       "//google_apis",
diff --git a/components/policy/core/common/BUILD.gn b/components/policy/core/common/BUILD.gn
index 8bd89b1..f432468 100644
--- a/components/policy/core/common/BUILD.gn
+++ b/components/policy/core/common/BUILD.gn
@@ -136,11 +136,11 @@
     ]
     deps = [
       "//base:i18n",
-      "//base:prefs",
       "//base/third_party/dynamic_annotations",
       "//components/data_use_measurement/core",
       "//components/json_schema",
       "//components/policy",
+      "//components/prefs",
       "//google_apis",
       "//net",
       "//third_party/re2",
@@ -283,10 +283,11 @@
 
     deps = [
       "//base",
-      "//base:prefs_test_support",
       "//base/test:test_support",
       "//components/policy",
       "//components/policy:policy_component_test_support",
+    "//components/prefs:test_support",
+      "//components/prefs:test_support",
       "//google_apis",
       "//net:test_support",
       "//testing/gmock",
diff --git a/components/policy/policy_browser.gypi b/components/policy/policy_browser.gypi
index 9012fbc..6b2b6c0 100644
--- a/components/policy/policy_browser.gypi
+++ b/components/policy/policy_browser.gypi
@@ -5,7 +5,6 @@
 {
   'dependencies': [
     '../base/base.gyp:base',
-    '../base/base.gyp:base_prefs',
     '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
     '../net/net.gyp:net',
     '../ui/base/ui_base.gyp:ui_base',
@@ -15,6 +14,7 @@
     'components_strings.gyp:components_strings',
     'keyed_service_core',
     'pref_registry',
+    'prefs/prefs.gyp:prefs',
     'url_matcher',
   ],
   'defines': [
diff --git a/components/policy/policy_common.gypi b/components/policy/policy_common.gypi
index 55573e6..e9c7cb5 100644
--- a/components/policy/policy_common.gypi
+++ b/components/policy/policy_common.gypi
@@ -16,7 +16,6 @@
   'conditions': [
     ['configuration_policy==1', {
       'dependencies': [
-        '../base/base.gyp:base_prefs',
         '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
         '../google_apis/google_apis.gyp:google_apis',
         '../net/net.gyp:net',
@@ -26,6 +25,7 @@
         'data_use_measurement_core',
         'json_schema',
         'policy',
+        'prefs/prefs.gyp:prefs',
       ],
       'sources': [
         'core/common/async_policy_loader.cc',
diff --git a/components/precache/content/BUILD.gn b/components/precache/content/BUILD.gn
index ba87b185..297ec27d 100644
--- a/components/precache/content/BUILD.gn
+++ b/components/precache/content/BUILD.gn
@@ -12,10 +12,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/history/core/browser",
     "//components/keyed_service/core",
     "//components/precache/core",
+    "//components/prefs",
     "//components/sync_driver",
     "//components/variations",
     "//content/public/browser",
diff --git a/components/precache/core/BUILD.gn b/components/precache/core/BUILD.gn
index 5badf1d4..16f6ce84 100644
--- a/components/precache/core/BUILD.gn
+++ b/components/precache/core/BUILD.gn
@@ -38,8 +38,8 @@
   deps = [
     ":proto",
     "//base",
-    "//base:prefs",
     "//components/history/core/browser",
+    "//components/prefs",
     "//net",
     "//sql",
     "//url",
diff --git a/components/pref_registry.gypi b/components/pref_registry.gypi
index 5ff32c38..0499e19 100644
--- a/components/pref_registry.gypi
+++ b/components/pref_registry.gypi
@@ -10,8 +10,8 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
@@ -27,7 +27,7 @@
       'type': 'static_library',
       'dependencies': [
         'pref_registry',
-        '../base/base.gyp:base_prefs_test_support',
+        'prefs/prefs.gyp:prefs_test_support',
       ],
       'include_dirs': [
         '..',
diff --git a/components/pref_registry/BUILD.gn b/components/pref_registry/BUILD.gn
index c3ce504..8a3ef8b 100644
--- a/components/pref_registry/BUILD.gn
+++ b/components/pref_registry/BUILD.gn
@@ -10,8 +10,8 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//base/third_party/dynamic_annotations",
+    "//components/prefs",
   ]
 }
 
@@ -28,7 +28,6 @@
 
   deps = [
     "//base",
-    "//base:prefs",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
   ]
 }
diff --git a/components/prefs/BUILD.gn b/components/prefs/BUILD.gn
new file mode 100644
index 0000000..0919fe33
--- /dev/null
+++ b/components/prefs/BUILD.gn
@@ -0,0 +1,137 @@
+# Copyright 2015 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+component("prefs") {
+  sources = [
+    # Reference the forwarding headers so "gn check" can check them properly
+    # while we're transitioning from base to here.
+    "//base/prefs/base_prefs_export.h",
+    "//base/prefs/default_pref_store.h",
+    "//base/prefs/json_pref_store.h",
+    "//base/prefs/overlay_user_pref_store.h",
+    "//base/prefs/persistent_pref_store.h",
+    "//base/prefs/pref_change_registrar.h",
+    "//base/prefs/pref_filter.h",
+    "//base/prefs/pref_member.h",
+    "//base/prefs/pref_notifier.h",
+    "//base/prefs/pref_notifier_impl.h",
+    "//base/prefs/pref_observer.h",
+    "//base/prefs/pref_registry.h",
+    "//base/prefs/pref_registry_simple.h",
+    "//base/prefs/pref_service_factory.h",
+    "//base/prefs/pref_service.h",
+    "//base/prefs/pref_store.h",
+    "//base/prefs/pref_value_map.h",
+    "//base/prefs/pref_value_store.h",
+    "//base/prefs/scoped_user_pref_update.h",
+    "//base/prefs/value_map_pref_store.h",
+    "//base/prefs/writeable_pref_store.h",
+
+    "default_pref_store.cc",
+    "default_pref_store.h",
+    "json_pref_store.cc",
+    "json_pref_store.h",
+    "overlay_user_pref_store.cc",
+    "overlay_user_pref_store.h",
+    "pref_change_registrar.cc",
+    "pref_change_registrar.h",
+    "pref_member.cc",
+    "pref_member.h",
+    "pref_notifier_impl.cc",
+    "pref_notifier_impl.h",
+    "pref_registry.cc",
+    "pref_registry.h",
+    "pref_registry_simple.cc",
+    "pref_registry_simple.h",
+    "pref_service.cc",
+    "pref_service.h",
+    "pref_service_factory.cc",
+    "pref_service_factory.h",
+    "pref_store.cc",
+    "pref_store.h",
+    "pref_value_map.cc",
+    "pref_value_map.h",
+    "pref_value_store.cc",
+    "pref_value_store.h",
+    "scoped_user_pref_update.cc",
+    "scoped_user_pref_update.h",
+    "value_map_pref_store.cc",
+    "value_map_pref_store.h",
+  ]
+  if (!is_ios) {
+    sources += [
+      "base_prefs_export.h",
+      "persistent_pref_store.h",
+      "pref_filter.h",
+      "pref_notifier.h",
+      "pref_observer.h",
+      "writeable_pref_store.h",
+    ]
+  }
+
+  defines = [ "BASE_PREFS_IMPLEMENTATION" ]
+
+  deps = [
+    "//base",
+  ]
+
+  if (!is_debug) {
+    configs -= [ "//build/config/compiler:default_optimization" ]
+    configs += [ "//build/config/compiler:optimize_max" ]
+  }
+}
+
+source_set("test_support") {
+  testonly = true
+  sources = [
+    # Reference the forwarding headers so "gn check" can check them properly
+    # while we're transitioning from base to here.
+    "//base/prefs/mock_pref_change_callback.h",
+    "//base/prefs/pref_store_observer_mock.h",
+    "//base/prefs/testing_pref_service.h",
+    "//base/prefs/testing_pref_store.h",
+
+    "mock_pref_change_callback.cc",
+    "mock_pref_change_callback.h",
+    "pref_store_observer_mock.cc",
+    "pref_store_observer_mock.h",
+    "testing_pref_service.cc",
+    "testing_pref_service.h",
+    "testing_pref_store.cc",
+    "testing_pref_store.h",
+  ]
+
+  public_deps = [
+    ":prefs",
+  ]
+  deps = [
+    "//base",
+    "//testing/gmock",
+    "//testing/gtest",
+  ]
+}
+
+source_set("unit_tests") {
+  testonly = true
+  sources = [
+    "default_pref_store_unittest.cc",
+    "json_pref_store_unittest.cc",
+    "overlay_user_pref_store_unittest.cc",
+    "pref_change_registrar_unittest.cc",
+    "pref_member_unittest.cc",
+    "pref_notifier_impl_unittest.cc",
+    "pref_service_unittest.cc",
+    "pref_value_map_unittest.cc",
+    "pref_value_store_unittest.cc",
+    "scoped_user_pref_update_unittest.cc",
+  ]
+
+  deps = [
+    ":test_support",
+    "//base",
+    "//base/test:test_support",
+    "//testing/gmock",
+    "//testing/gtest",
+  ]
+}
diff --git a/base/prefs/OWNERS b/components/prefs/OWNERS
similarity index 100%
rename from base/prefs/OWNERS
rename to components/prefs/OWNERS
diff --git a/components/prefs/base_prefs_export.h b/components/prefs/base_prefs_export.h
new file mode 100644
index 0000000..3d207db
--- /dev/null
+++ b/components/prefs/base_prefs_export.h
@@ -0,0 +1,29 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_BASE_PREFS_EXPORT_H_
+#define BASE_PREFS_BASE_PREFS_EXPORT_H_
+
+#if defined(COMPONENT_BUILD)
+#if defined(WIN32)
+
+#if defined(BASE_PREFS_IMPLEMENTATION)
+#define BASE_PREFS_EXPORT __declspec(dllexport)
+#else
+#define BASE_PREFS_EXPORT __declspec(dllimport)
+#endif  // defined(BASE_PREFS_IMPLEMENTATION)
+
+#else  // defined(WIN32)
+#if defined(BASE_PREFS_IMPLEMENTATION)
+#define BASE_PREFS_EXPORT __attribute__((visibility("default")))
+#else
+#define BASE_PREFS_EXPORT
+#endif
+#endif
+
+#else  // defined(COMPONENT_BUILD)
+#define BASE_PREFS_EXPORT
+#endif
+
+#endif  // BASE_PREFS_BASE_PREFS_EXPORT_H_
diff --git a/base/prefs/default_pref_store.cc b/components/prefs/default_pref_store.cc
similarity index 100%
rename from base/prefs/default_pref_store.cc
rename to components/prefs/default_pref_store.cc
diff --git a/components/prefs/default_pref_store.h b/components/prefs/default_pref_store.h
new file mode 100644
index 0000000..ac5364d
--- /dev/null
+++ b/components/prefs/default_pref_store.h
@@ -0,0 +1,53 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_DEFAULT_PREF_STORE_H_
+#define BASE_PREFS_DEFAULT_PREF_STORE_H_
+
+#include <string>
+
+#include "base/macros.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_store.h"
+#include "base/prefs/pref_value_map.h"
+#include "base/values.h"
+
+// Used within a PrefRegistry to keep track of default preference values.
+class BASE_PREFS_EXPORT DefaultPrefStore : public PrefStore {
+ public:
+  typedef PrefValueMap::const_iterator const_iterator;
+
+  DefaultPrefStore();
+
+  // PrefStore implementation:
+  bool GetValue(const std::string& key,
+                const base::Value** result) const override;
+  void AddObserver(PrefStore::Observer* observer) override;
+  void RemoveObserver(PrefStore::Observer* observer) override;
+  bool HasObservers() const override;
+
+  // Sets a |value| for |key|. Should only be called if a value has not been
+  // set yet; otherwise call ReplaceDefaultValue().
+  void SetDefaultValue(const std::string& key, scoped_ptr<base::Value> value);
+
+  // Replaces the the value for |key| with a new value. Should only be called
+  // if a value has alreday been set; otherwise call SetDefaultValue().
+  void ReplaceDefaultValue(const std::string& key,
+                           scoped_ptr<base::Value> value);
+
+  const_iterator begin() const;
+  const_iterator end() const;
+
+ private:
+  ~DefaultPrefStore() override;
+
+  PrefValueMap prefs_;
+
+  base::ObserverList<PrefStore::Observer, true> observers_;
+
+  DISALLOW_COPY_AND_ASSIGN(DefaultPrefStore);
+};
+
+#endif  // BASE_PREFS_DEFAULT_PREF_STORE_H_
diff --git a/base/prefs/default_pref_store_unittest.cc b/components/prefs/default_pref_store_unittest.cc
similarity index 100%
rename from base/prefs/default_pref_store_unittest.cc
rename to components/prefs/default_pref_store_unittest.cc
diff --git a/base/prefs/json_pref_store.cc b/components/prefs/json_pref_store.cc
similarity index 100%
rename from base/prefs/json_pref_store.cc
rename to components/prefs/json_pref_store.cc
diff --git a/components/prefs/json_pref_store.h b/components/prefs/json_pref_store.h
new file mode 100644
index 0000000..6342977
--- /dev/null
+++ b/components/prefs/json_pref_store.h
@@ -0,0 +1,229 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_JSON_PREF_STORE_H_
+#define BASE_PREFS_JSON_PREF_STORE_H_
+
+#include <stdint.h>
+
+#include <set>
+#include <string>
+
+#include "base/callback_forward.h"
+#include "base/compiler_specific.h"
+#include "base/files/file_path.h"
+#include "base/files/important_file_writer.h"
+#include "base/gtest_prod_util.h"
+#include "base/macros.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/memory/weak_ptr.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/persistent_pref_store.h"
+#include "base/threading/non_thread_safe.h"
+
+class PrefFilter;
+
+namespace base {
+class Clock;
+class DictionaryValue;
+class FilePath;
+class HistogramBase;
+class JsonPrefStoreLossyWriteTest;
+class SequencedTaskRunner;
+class SequencedWorkerPool;
+class Value;
+FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestBasic);
+FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestSinglePeriod);
+FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestMultiplePeriods);
+FORWARD_DECLARE_TEST(JsonPrefStoreTest, WriteCountHistogramTestPeriodWithGaps);
+}
+
+// A writable PrefStore implementation that is used for user preferences.
+class BASE_PREFS_EXPORT JsonPrefStore
+    : public PersistentPrefStore,
+      public base::ImportantFileWriter::DataSerializer,
+      public base::SupportsWeakPtr<JsonPrefStore>,
+      public base::NonThreadSafe {
+ public:
+  struct ReadResult;
+
+  // Returns instance of SequencedTaskRunner which guarantees that file
+  // operations on the same file will be executed in sequenced order.
+  static scoped_refptr<base::SequencedTaskRunner> GetTaskRunnerForFile(
+      const base::FilePath& pref_filename,
+      base::SequencedWorkerPool* worker_pool);
+
+  // Same as the constructor below with no alternate filename.
+  JsonPrefStore(
+      const base::FilePath& pref_filename,
+      const scoped_refptr<base::SequencedTaskRunner>& sequenced_task_runner,
+      scoped_ptr<PrefFilter> pref_filter);
+
+  // |sequenced_task_runner| must be a shutdown-blocking task runner, ideally
+  // created by the GetTaskRunnerForFile() method above.
+  // |pref_filename| is the path to the file to read prefs from.
+  // |pref_alternate_filename| is the path to an alternate file which the
+  // desired prefs may have previously been written to. If |pref_filename|
+  // doesn't exist and |pref_alternate_filename| does, |pref_alternate_filename|
+  // will be moved to |pref_filename| before the read occurs.
+  JsonPrefStore(
+      const base::FilePath& pref_filename,
+      const base::FilePath& pref_alternate_filename,
+      const scoped_refptr<base::SequencedTaskRunner>& sequenced_task_runner,
+      scoped_ptr<PrefFilter> pref_filter);
+
+  // PrefStore overrides:
+  bool GetValue(const std::string& key,
+                const base::Value** result) const override;
+  void AddObserver(PrefStore::Observer* observer) override;
+  void RemoveObserver(PrefStore::Observer* observer) override;
+  bool HasObservers() const override;
+  bool IsInitializationComplete() const override;
+
+  // PersistentPrefStore overrides:
+  bool GetMutableValue(const std::string& key, base::Value** result) override;
+  void SetValue(const std::string& key,
+                scoped_ptr<base::Value> value,
+                uint32_t flags) override;
+  void SetValueSilently(const std::string& key,
+                        scoped_ptr<base::Value> value,
+                        uint32_t flags) override;
+  void RemoveValue(const std::string& key, uint32_t flags) override;
+  bool ReadOnly() const override;
+  PrefReadError GetReadError() const override;
+  // Note this method may be asynchronous if this instance has a |pref_filter_|
+  // in which case it will return PREF_READ_ERROR_ASYNCHRONOUS_TASK_INCOMPLETE.
+  // See details in pref_filter.h.
+  PrefReadError ReadPrefs() override;
+  void ReadPrefsAsync(ReadErrorDelegate* error_delegate) override;
+  void CommitPendingWrite() override;
+  void SchedulePendingLossyWrites() override;
+  void ReportValueChanged(const std::string& key, uint32_t flags) override;
+
+  // Just like RemoveValue(), but doesn't notify observers. Used when doing some
+  // cleanup that shouldn't otherwise alert observers.
+  void RemoveValueSilently(const std::string& key, uint32_t flags);
+
+  // Registers |on_next_successful_write| to be called once, on the next
+  // successful write event of |writer_|.
+  void RegisterOnNextSuccessfulWriteCallback(
+      const base::Closure& on_next_successful_write);
+
+ private:
+  // Represents a histogram for recording the number of writes to the pref file
+  // that occur every kHistogramWriteReportIntervalInMins minutes.
+  class BASE_PREFS_EXPORT WriteCountHistogram {
+   public:
+    static const int32_t kHistogramWriteReportIntervalMins;
+
+    WriteCountHistogram(const base::TimeDelta& commit_interval,
+                        const base::FilePath& path);
+    // Constructor for testing. |clock| is a test Clock that is used to retrieve
+    // the time.
+    WriteCountHistogram(const base::TimeDelta& commit_interval,
+                        const base::FilePath& path,
+                        scoped_ptr<base::Clock> clock);
+    ~WriteCountHistogram();
+
+    // Record that a write has occured.
+    void RecordWriteOccured();
+
+    // Reports writes (that have not yet been reported) in all of the recorded
+    // intervals that have elapsed up until current time.
+    void ReportOutstandingWrites();
+
+    base::HistogramBase* GetHistogram();
+
+   private:
+    // The minimum interval at which writes can occur.
+    const base::TimeDelta commit_interval_;
+
+    // The path to the file.
+    const base::FilePath path_;
+
+    // Clock which is used to retrieve the current time.
+    scoped_ptr<base::Clock> clock_;
+
+    // The interval at which to report write counts.
+    const base::TimeDelta report_interval_;
+
+    // The time at which the last histogram value was reported for the number
+    // of write counts.
+    base::Time last_report_time_;
+
+    // The number of writes that have occured since the last write count was
+    // reported.
+    uint32_t writes_since_last_report_;
+
+    DISALLOW_COPY_AND_ASSIGN(WriteCountHistogram);
+  };
+
+  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
+                           WriteCountHistogramTestBasic);
+  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
+                           WriteCountHistogramTestSinglePeriod);
+  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
+                           WriteCountHistogramTestMultiplePeriods);
+  FRIEND_TEST_ALL_PREFIXES(base::JsonPrefStoreTest,
+                           WriteCountHistogramTestPeriodWithGaps);
+  friend class base::JsonPrefStoreLossyWriteTest;
+
+  ~JsonPrefStore() override;
+
+  // This method is called after the JSON file has been read.  It then hands
+  // |value| (or an empty dictionary in some read error cases) to the
+  // |pref_filter| if one is set. It also gives a callback pointing at
+  // FinalizeFileRead() to that |pref_filter_| which is then responsible for
+  // invoking it when done. If there is no |pref_filter_|, FinalizeFileRead()
+  // is invoked directly.
+  void OnFileRead(scoped_ptr<ReadResult> read_result);
+
+  // ImportantFileWriter::DataSerializer overrides:
+  bool SerializeData(std::string* output) override;
+
+  // This method is called after the JSON file has been read and the result has
+  // potentially been intercepted and modified by |pref_filter_|.
+  // |initialization_successful| is pre-determined by OnFileRead() and should
+  // be used when reporting OnInitializationCompleted().
+  // |schedule_write| indicates whether a write should be immediately scheduled
+  // (typically because the |pref_filter_| has already altered the |prefs|) --
+  // this will be ignored if this store is read-only.
+  void FinalizeFileRead(bool initialization_successful,
+                        scoped_ptr<base::DictionaryValue> prefs,
+                        bool schedule_write);
+
+  // Schedule a write with the file writer as long as |flags| doesn't contain
+  // WriteablePrefStore::LOSSY_PREF_WRITE_FLAG.
+  void ScheduleWrite(uint32_t flags);
+
+  const base::FilePath path_;
+  const base::FilePath alternate_path_;
+  const scoped_refptr<base::SequencedTaskRunner> sequenced_task_runner_;
+
+  scoped_ptr<base::DictionaryValue> prefs_;
+
+  bool read_only_;
+
+  // Helper for safely writing pref data.
+  base::ImportantFileWriter writer_;
+
+  scoped_ptr<PrefFilter> pref_filter_;
+  base::ObserverList<PrefStore::Observer, true> observers_;
+
+  scoped_ptr<ReadErrorDelegate> error_delegate_;
+
+  bool initialized_;
+  bool filtering_in_progress_;
+  bool pending_lossy_write_;
+  PrefReadError read_error_;
+
+  std::set<std::string> keys_need_empty_value_;
+
+  WriteCountHistogram write_count_histogram_;
+
+  DISALLOW_COPY_AND_ASSIGN(JsonPrefStore);
+};
+
+#endif  // BASE_PREFS_JSON_PREF_STORE_H_
diff --git a/base/prefs/json_pref_store_unittest.cc b/components/prefs/json_pref_store_unittest.cc
similarity index 87%
rename from base/prefs/json_pref_store_unittest.cc
rename to components/prefs/json_pref_store_unittest.cc
index 41cad89..bc9eecaa 100644
--- a/base/prefs/json_pref_store_unittest.cc
+++ b/components/prefs/json_pref_store_unittest.cc
@@ -17,7 +17,6 @@
 #include "base/memory/scoped_ptr.h"
 #include "base/message_loop/message_loop.h"
 #include "base/metrics/histogram_samples.h"
-#include "base/metrics/statistics_recorder.h"
 #include "base/path_service.h"
 #include "base/prefs/pref_filter.h"
 #include "base/run_loop.h"
@@ -25,6 +24,7 @@
 #include "base/strings/string_number_conversions.h"
 #include "base/strings/string_util.h"
 #include "base/strings/utf_string_conversions.h"
+#include "base/test/histogram_tester.h"
 #include "base/test/simple_test_clock.h"
 #include "base/threading/sequenced_worker_pool.h"
 #include "base/threading/thread.h"
@@ -37,6 +37,25 @@
 
 const char kHomePage[] = "homepage";
 
+const char kReadJson[] =
+    "{\n"
+    "  \"homepage\": \"http://www.cnn.com\",\n"
+    "  \"some_directory\": \"/usr/local/\",\n"
+    "  \"tabs\": {\n"
+    "    \"new_windows_in_tabs\": true,\n"
+    "    \"max_tabs\": 20\n"
+    "  }\n"
+    "}";
+
+const char kInvalidJson[] = "!@#$%^&";
+
+// Expected output for tests using RunBasicJsonPrefStoreTest().
+const char kWriteGolden[] =
+    "{\"homepage\":\"http://www.cnn.com\","
+     "\"long_int\":{\"pref\":\"214748364842\"},"
+     "\"some_directory\":\"/usr/sbin/\","
+     "\"tabs\":{\"max_tabs\":10,\"new_windows_in_tabs\":false}}";
+
 // Set the time on the given SimpleTestClock to the given time in minutes.
 void SetCurrentTimeInMinutes(double minutes, base::SimpleTestClock* clock) {
   const int32_t kBaseTimeMins = 100;
@@ -104,10 +123,6 @@
  protected:
   void SetUp() override {
     ASSERT_TRUE(temp_dir_.CreateUniqueTempDir());
-
-    ASSERT_TRUE(PathService::Get(base::DIR_TEST_DATA, &data_dir_));
-    data_dir_ = data_dir_.AppendASCII("prefs");
-    ASSERT_TRUE(PathExists(data_dir_));
   }
 
   void TearDown() override {
@@ -118,14 +133,8 @@
 
   // The path to temporary directory used to contain the test operations.
   base::ScopedTempDir temp_dir_;
-  // The path to the directory where the test data is stored.
-  base::FilePath data_dir_;
   // A message loop that we can use as the file thread message loop.
   MessageLoop message_loop_;
-
- private:
-  // Ensure histograms are reset for each test.
-  StatisticsRecorder statistics_recorder_;
 };
 
 // Test fallback behavior for a nonexistent file.
@@ -156,9 +165,10 @@
 
 // Test fallback behavior for an invalid file.
 TEST_F(JsonPrefStoreTest, InvalidFile) {
-  base::FilePath invalid_file_original = data_dir_.AppendASCII("invalid.json");
   base::FilePath invalid_file = temp_dir_.path().AppendASCII("invalid.json");
-  ASSERT_TRUE(base::CopyFile(invalid_file_original, invalid_file));
+  ASSERT_LT(0, base::WriteFile(invalid_file,
+                               kInvalidJson, arraysize(kInvalidJson) - 1));
+
   scoped_refptr<JsonPrefStore> pref_store = new JsonPrefStore(
       invalid_file, message_loop_.task_runner(), scoped_ptr<PrefFilter>());
   EXPECT_EQ(PersistentPrefStore::PREF_READ_ERROR_JSON_PARSE,
@@ -169,14 +179,17 @@
   EXPECT_FALSE(PathExists(invalid_file));
   base::FilePath moved_aside = temp_dir_.path().AppendASCII("invalid.bad");
   EXPECT_TRUE(PathExists(moved_aside));
-  EXPECT_TRUE(TextContentsEqual(invalid_file_original, moved_aside));
+
+  std::string moved_aside_contents;
+  ASSERT_TRUE(base::ReadFileToString(moved_aside, &moved_aside_contents));
+  EXPECT_EQ(kInvalidJson, moved_aside_contents);
 }
 
-// This function is used to avoid code duplication while testing synchronous and
-// asynchronous version of the JsonPrefStore loading.
+// This function is used to avoid code duplication while testing synchronous
+// and asynchronous version of the JsonPrefStore loading. It validates that the
+// given output file's contents matches kWriteGolden.
 void RunBasicJsonPrefStoreTest(JsonPrefStore* pref_store,
-                               const base::FilePath& output_file,
-                               const base::FilePath& golden_output_file) {
+                               const base::FilePath& output_file) {
   const char kNewWindowsInTabs[] = "tabs.new_windows_in_tabs";
   const char kMaxTabs[] = "tabs.max_tabs";
   const char kLongIntPref[] = "long_int.pref";
@@ -238,19 +251,21 @@
   EXPECT_EQ(214748364842LL, value);
 
   // Serialize and compare to expected output.
-  ASSERT_TRUE(PathExists(golden_output_file));
   pref_store->CommitPendingWrite();
   RunLoop().RunUntilIdle();
-  EXPECT_TRUE(TextContentsEqual(golden_output_file, output_file));
+
+  std::string output_contents;
+  ASSERT_TRUE(base::ReadFileToString(output_file, &output_contents));
+  EXPECT_EQ(kWriteGolden, output_contents);
   ASSERT_TRUE(base::DeleteFile(output_file, false));
 }
 
 TEST_F(JsonPrefStoreTest, Basic) {
-  ASSERT_TRUE(base::CopyFile(data_dir_.AppendASCII("read.json"),
-                             temp_dir_.path().AppendASCII("write.json")));
+  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   // Test that the persistent value can be loaded.
-  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
   ASSERT_TRUE(PathExists(input_file));
   scoped_refptr<JsonPrefStore> pref_store = new JsonPrefStore(
       input_file, message_loop_.task_runner(), scoped_ptr<PrefFilter>());
@@ -268,17 +283,15 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, BasicAsync) {
-  ASSERT_TRUE(base::CopyFile(data_dir_.AppendASCII("read.json"),
-                             temp_dir_.path().AppendASCII("write.json")));
+  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   // Test that the persistent value can be loaded.
-  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  ASSERT_TRUE(PathExists(input_file));
   scoped_refptr<JsonPrefStore> pref_store = new JsonPrefStore(
       input_file, message_loop_.task_runner(), scoped_ptr<PrefFilter>());
 
@@ -309,8 +322,7 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, PreserveEmptyValues) {
@@ -386,12 +398,9 @@
 }
 
 TEST_F(JsonPrefStoreTest, ReadWithInterceptor) {
-  ASSERT_TRUE(base::CopyFile(data_dir_.AppendASCII("read.json"),
-                             temp_dir_.path().AppendASCII("write.json")));
-
-  // Test that the persistent value can be loaded.
   base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  ASSERT_TRUE(PathExists(input_file));
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   scoped_ptr<InterceptingPrefFilter> intercepting_pref_filter(
       new InterceptingPrefFilter());
@@ -427,17 +436,13 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, ReadAsyncWithInterceptor) {
-  ASSERT_TRUE(base::CopyFile(data_dir_.AppendASCII("read.json"),
-                             temp_dir_.path().AppendASCII("write.json")));
-
-  // Test that the persistent value can be loaded.
   base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  ASSERT_TRUE(PathExists(input_file));
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   scoped_ptr<InterceptingPrefFilter> intercepting_pref_filter(
       new InterceptingPrefFilter());
@@ -492,20 +497,18 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, AlternateFile) {
-  ASSERT_TRUE(
-      base::CopyFile(data_dir_.AppendASCII("read.json"),
-                     temp_dir_.path().AppendASCII("alternate.json")));
+  base::FilePath alternate_input_file =
+      temp_dir_.path().AppendASCII("alternate.json");
+  ASSERT_LT(0, base::WriteFile(alternate_input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   // Test that the alternate file is moved to the main file and read as-is from
   // there.
   base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  base::FilePath alternate_input_file =
-      temp_dir_.path().AppendASCII("alternate.json");
   ASSERT_FALSE(PathExists(input_file));
   ASSERT_TRUE(PathExists(alternate_input_file));
   scoped_refptr<JsonPrefStore> pref_store =
@@ -532,26 +535,22 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, AlternateFileIgnoredWhenMainFileExists) {
-  ASSERT_TRUE(
-      base::CopyFile(data_dir_.AppendASCII("read.json"),
-                     temp_dir_.path().AppendASCII("write.json")));
-  ASSERT_TRUE(
-      base::CopyFile(data_dir_.AppendASCII("invalid.json"),
-                     temp_dir_.path().AppendASCII("alternate.json")));
+  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
+
+  base::FilePath alternate_input_file =
+      temp_dir_.path().AppendASCII("alternate.json");
+  ASSERT_LT(0, base::WriteFile(alternate_input_file,
+                               kInvalidJson, arraysize(kInvalidJson) - 1));
 
   // Test that the alternate file is ignored and that the read occurs from the
   // existing main file. There is no attempt at even deleting the alternate
   // file as this scenario should never happen in normal user-data-dirs.
-  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  base::FilePath alternate_input_file =
-      temp_dir_.path().AppendASCII("alternate.json");
-  ASSERT_TRUE(PathExists(input_file));
-  ASSERT_TRUE(PathExists(alternate_input_file));
   scoped_refptr<JsonPrefStore> pref_store =
       new JsonPrefStore(input_file, alternate_input_file,
                         message_loop_.task_runner(), scoped_ptr<PrefFilter>());
@@ -576,18 +575,16 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, AlternateFileDNE) {
-  ASSERT_TRUE(
-      base::CopyFile(data_dir_.AppendASCII("read.json"),
-                     temp_dir_.path().AppendASCII("write.json")));
+  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
+  ASSERT_LT(0, base::WriteFile(input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   // Test that the basic read works fine when an alternate file is specified but
   // does not exist.
-  base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
   base::FilePath alternate_input_file =
       temp_dir_.path().AppendASCII("alternate.json");
   ASSERT_TRUE(PathExists(input_file));
@@ -616,22 +613,18 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, BasicAsyncWithAlternateFile) {
-  ASSERT_TRUE(
-      base::CopyFile(data_dir_.AppendASCII("read.json"),
-                     temp_dir_.path().AppendASCII("alternate.json")));
+  base::FilePath alternate_input_file =
+      temp_dir_.path().AppendASCII("alternate.json");
+  ASSERT_LT(0, base::WriteFile(alternate_input_file,
+                               kReadJson, arraysize(kReadJson) - 1));
 
   // Test that the alternate file is moved to the main file and read as-is from
   // there even when the read is made asynchronously.
   base::FilePath input_file = temp_dir_.path().AppendASCII("write.json");
-  base::FilePath alternate_input_file =
-      temp_dir_.path().AppendASCII("alternate.json");
-  ASSERT_FALSE(PathExists(input_file));
-  ASSERT_TRUE(PathExists(alternate_input_file));
   scoped_refptr<JsonPrefStore> pref_store =
       new JsonPrefStore(input_file, alternate_input_file,
                         message_loop_.task_runner(), scoped_ptr<PrefFilter>());
@@ -669,11 +662,12 @@
   //   }
   // }
 
-  RunBasicJsonPrefStoreTest(
-      pref_store.get(), input_file, data_dir_.AppendASCII("write.golden.json"));
+  RunBasicJsonPrefStoreTest(pref_store.get(), input_file);
 }
 
 TEST_F(JsonPrefStoreTest, WriteCountHistogramTestBasic) {
+  base::HistogramTester histogram_tester;
+
   SimpleTestClock* test_clock = new SimpleTestClock;
   SetCurrentTimeInMinutes(0, test_clock);
   JsonPrefStore::WriteCountHistogram histogram(
@@ -689,8 +683,10 @@
   histogram.ReportOutstandingWrites();
   scoped_ptr<HistogramSamples> samples =
       histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(1, samples->GetCount(1));
-  ASSERT_EQ(1, samples->TotalCount());
+
+  std::string histogram_name = histogram.GetHistogram()->histogram_name();
+  histogram_tester.ExpectBucketCount(histogram_name, 1, 1);
+  histogram_tester.ExpectTotalCount(histogram_name, 1);
 
   ASSERT_EQ("Settings.JsonDataWriteCount.Local_State",
             histogram.GetHistogram()->histogram_name());
@@ -698,6 +694,8 @@
 }
 
 TEST_F(JsonPrefStoreTest, WriteCountHistogramTestSinglePeriod) {
+  base::HistogramTester histogram_tester;
+
   SimpleTestClock* test_clock = new SimpleTestClock;
   SetCurrentTimeInMinutes(0, test_clock);
   JsonPrefStore::WriteCountHistogram histogram(
@@ -714,29 +712,28 @@
   histogram.RecordWriteOccured();
 
   // Nothing should be recorded until the report period has elapsed.
-  scoped_ptr<HistogramSamples> samples =
-      histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(0, samples->TotalCount());
+  std::string histogram_name = histogram.GetHistogram()->histogram_name();
+  histogram_tester.ExpectTotalCount(histogram_name, 0);
 
   SetCurrentTimeInMinutes(1.3 * report_interval, test_clock);
   histogram.RecordWriteOccured();
 
   // Now the report period has elapsed.
-  samples = histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(1, samples->GetCount(3));
-  ASSERT_EQ(1, samples->TotalCount());
+  histogram_tester.ExpectBucketCount(histogram_name, 3, 1);
+  histogram_tester.ExpectTotalCount(histogram_name, 1);
 
   // The last write won't be recorded because the second count period hasn't
   // fully elapsed.
   SetCurrentTimeInMinutes(1.5 * report_interval, test_clock);
   histogram.ReportOutstandingWrites();
 
-  samples = histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(1, samples->GetCount(3));
-  ASSERT_EQ(1, samples->TotalCount());
+  histogram_tester.ExpectBucketCount(histogram_name, 3, 1);
+  histogram_tester.ExpectTotalCount(histogram_name, 1);
 }
 
 TEST_F(JsonPrefStoreTest, WriteCountHistogramTestMultiplePeriods) {
+  base::HistogramTester histogram_tester;
+
   SimpleTestClock* test_clock = new SimpleTestClock;
   SetCurrentTimeInMinutes(0, test_clock);
   JsonPrefStore::WriteCountHistogram histogram(
@@ -768,14 +765,15 @@
   // fully elapsed
   SetCurrentTimeInMinutes(3.5 * report_interval, test_clock);
   histogram.ReportOutstandingWrites();
-  scoped_ptr<HistogramSamples> samples =
-      histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(2, samples->GetCount(3));
-  ASSERT_EQ(1, samples->GetCount(2));
-  ASSERT_EQ(3, samples->TotalCount());
+  std::string histogram_name = histogram.GetHistogram()->histogram_name();
+  histogram_tester.ExpectBucketCount(histogram_name, 3, 2);
+  histogram_tester.ExpectBucketCount(histogram_name, 2, 1);
+  histogram_tester.ExpectTotalCount(histogram_name, 3);
 }
 
 TEST_F(JsonPrefStoreTest, WriteCountHistogramTestPeriodWithGaps) {
+  base::HistogramTester histogram_tester;
+
   SimpleTestClock* test_clock = new SimpleTestClock;
   SetCurrentTimeInMinutes(0, test_clock);
   JsonPrefStore::WriteCountHistogram histogram(
@@ -808,13 +806,12 @@
 
   SetCurrentTimeInMinutes(6.1 * report_interval, test_clock);
   histogram.ReportOutstandingWrites();
-  scoped_ptr<HistogramSamples> samples =
-      histogram.GetHistogram()->SnapshotSamples();
-  ASSERT_EQ(3, samples->GetCount(0));
-  ASSERT_EQ(1, samples->GetCount(1));
-  ASSERT_EQ(1, samples->GetCount(2));
-  ASSERT_EQ(1, samples->GetCount(3));
-  ASSERT_EQ(6, samples->TotalCount());
+  std::string histogram_name = histogram.GetHistogram()->histogram_name();
+  histogram_tester.ExpectBucketCount(histogram_name, 0, 3);
+  histogram_tester.ExpectBucketCount(histogram_name, 1, 1);
+  histogram_tester.ExpectBucketCount(histogram_name, 2, 1);
+  histogram_tester.ExpectBucketCount(histogram_name, 3, 1);
+  histogram_tester.ExpectTotalCount(histogram_name, 6);
 }
 
 class JsonPrefStoreLossyWriteTest : public JsonPrefStoreTest {
diff --git a/base/prefs/mock_pref_change_callback.cc b/components/prefs/mock_pref_change_callback.cc
similarity index 100%
rename from base/prefs/mock_pref_change_callback.cc
rename to components/prefs/mock_pref_change_callback.cc
diff --git a/components/prefs/mock_pref_change_callback.h b/components/prefs/mock_pref_change_callback.h
new file mode 100644
index 0000000..3030fab1
--- /dev/null
+++ b/components/prefs/mock_pref_change_callback.h
@@ -0,0 +1,51 @@
+// Copyright (c) 2011 The Chromium 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 BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
+#define BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
+
+#include <string>
+
+#include "base/prefs/pref_change_registrar.h"
+#include "base/prefs/pref_service.h"
+#include "testing/gmock/include/gmock/gmock.h"
+
+using testing::Pointee;
+using testing::Property;
+using testing::Truly;
+
+// Matcher that checks whether the current value of the preference named
+// |pref_name| in |prefs| matches |value|. If |value| is NULL, the matcher
+// checks that the value is not set.
+MATCHER_P3(PrefValueMatches, prefs, pref_name, value, "") {
+  const PrefService::Preference* pref = prefs->FindPreference(pref_name);
+  if (!pref)
+    return false;
+
+  const base::Value* actual_value = pref->GetValue();
+  if (!actual_value)
+    return value == NULL;
+  if (!value)
+    return actual_value == NULL;
+  return value->Equals(actual_value);
+}
+
+// A mock for testing preference notifications and easy setup of expectations.
+class MockPrefChangeCallback {
+ public:
+  explicit MockPrefChangeCallback(PrefService* prefs);
+  virtual ~MockPrefChangeCallback();
+
+  PrefChangeRegistrar::NamedChangeCallback GetCallback();
+
+  MOCK_METHOD1(OnPreferenceChanged, void(const std::string&));
+
+  void Expect(const std::string& pref_name,
+              const base::Value* value);
+
+ private:
+  PrefService* prefs_;
+};
+
+#endif  // BASE_PREFS_MOCK_PREF_CHANGE_CALLBACK_H_
diff --git a/base/prefs/overlay_user_pref_store.cc b/components/prefs/overlay_user_pref_store.cc
similarity index 100%
rename from base/prefs/overlay_user_pref_store.cc
rename to components/prefs/overlay_user_pref_store.cc
diff --git a/components/prefs/overlay_user_pref_store.h b/components/prefs/overlay_user_pref_store.h
new file mode 100644
index 0000000..35ada57
--- /dev/null
+++ b/components/prefs/overlay_user_pref_store.h
@@ -0,0 +1,89 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
+#define BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
+
+#include <stdint.h>
+
+#include <map>
+#include <string>
+
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/persistent_pref_store.h"
+#include "base/prefs/pref_value_map.h"
+
+// PersistentPrefStore that directs all write operations into an in-memory
+// PrefValueMap. Read operations are first answered by the PrefValueMap.
+// If the PrefValueMap does not contain a value for the requested key,
+// the look-up is passed on to an underlying PersistentPrefStore |underlay_|.
+class BASE_PREFS_EXPORT OverlayUserPrefStore : public PersistentPrefStore,
+                                               public PrefStore::Observer {
+ public:
+  explicit OverlayUserPrefStore(PersistentPrefStore* underlay);
+
+  // Returns true if a value has been set for the |key| in this
+  // OverlayUserPrefStore, i.e. if it potentially overrides a value
+  // from the |underlay_|.
+  virtual bool IsSetInOverlay(const std::string& key) const;
+
+  // Methods of PrefStore.
+  void AddObserver(PrefStore::Observer* observer) override;
+  void RemoveObserver(PrefStore::Observer* observer) override;
+  bool HasObservers() const override;
+  bool IsInitializationComplete() const override;
+  bool GetValue(const std::string& key,
+                const base::Value** result) const override;
+
+  // Methods of PersistentPrefStore.
+  bool GetMutableValue(const std::string& key, base::Value** result) override;
+  void SetValue(const std::string& key,
+                scoped_ptr<base::Value> value,
+                uint32_t flags) override;
+  void SetValueSilently(const std::string& key,
+                        scoped_ptr<base::Value> value,
+                        uint32_t flags) override;
+  void RemoveValue(const std::string& key, uint32_t flags) override;
+  bool ReadOnly() const override;
+  PrefReadError GetReadError() const override;
+  PrefReadError ReadPrefs() override;
+  void ReadPrefsAsync(ReadErrorDelegate* delegate) override;
+  void CommitPendingWrite() override;
+  void SchedulePendingLossyWrites() override;
+  void ReportValueChanged(const std::string& key, uint32_t flags) override;
+
+  // Methods of PrefStore::Observer.
+  void OnPrefValueChanged(const std::string& key) override;
+  void OnInitializationCompleted(bool succeeded) override;
+
+  void RegisterOverlayPref(const std::string& key);
+  void RegisterOverlayPref(const std::string& overlay_key,
+                           const std::string& underlay_key);
+
+ protected:
+  ~OverlayUserPrefStore() override;
+
+ private:
+  typedef std::map<std::string, std::string> NamesMap;
+
+  const std::string& GetOverlayKey(const std::string& underlay_key) const;
+  const std::string& GetUnderlayKey(const std::string& overlay_key) const;
+
+  // Returns true if |key| corresponds to a preference that shall be stored in
+  // an in-memory PrefStore that is not persisted to disk.
+  bool ShallBeStoredInOverlay(const std::string& key) const;
+
+  base::ObserverList<PrefStore::Observer, true> observers_;
+  PrefValueMap overlay_;
+  scoped_refptr<PersistentPrefStore> underlay_;
+  NamesMap overlay_to_underlay_names_map_;
+  NamesMap underlay_to_overlay_names_map_;
+
+  DISALLOW_COPY_AND_ASSIGN(OverlayUserPrefStore);
+};
+
+#endif  // BASE_PREFS_OVERLAY_USER_PREF_STORE_H_
diff --git a/base/prefs/overlay_user_pref_store_unittest.cc b/components/prefs/overlay_user_pref_store_unittest.cc
similarity index 100%
rename from base/prefs/overlay_user_pref_store_unittest.cc
rename to components/prefs/overlay_user_pref_store_unittest.cc
diff --git a/components/prefs/persistent_pref_store.h b/components/prefs/persistent_pref_store.h
new file mode 100644
index 0000000..89c7a71
--- /dev/null
+++ b/components/prefs/persistent_pref_store.h
@@ -0,0 +1,77 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PERSISTENT_PREF_STORE_H_
+#define BASE_PREFS_PERSISTENT_PREF_STORE_H_
+
+#include <string>
+
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/writeable_pref_store.h"
+
+// This interface is complementary to the PrefStore interface, declaring
+// additional functionality that adds support for setting values and persisting
+// the data to some backing store.
+class BASE_PREFS_EXPORT PersistentPrefStore : public WriteablePrefStore {
+ public:
+  // Unique integer code for each type of error so we can report them
+  // distinctly in a histogram.
+  // NOTE: Don't change the explicit values of the enums as it will change the
+  // server's meaning of the histogram.
+  enum PrefReadError {
+    PREF_READ_ERROR_NONE = 0,
+    PREF_READ_ERROR_JSON_PARSE = 1,
+    PREF_READ_ERROR_JSON_TYPE = 2,
+    PREF_READ_ERROR_ACCESS_DENIED = 3,
+    PREF_READ_ERROR_FILE_OTHER = 4,
+    PREF_READ_ERROR_FILE_LOCKED = 5,
+    PREF_READ_ERROR_NO_FILE = 6,
+    PREF_READ_ERROR_JSON_REPEAT = 7,
+    // PREF_READ_ERROR_OTHER = 8,  // Deprecated.
+    PREF_READ_ERROR_FILE_NOT_SPECIFIED = 9,
+    // Indicates that ReadPrefs() couldn't complete synchronously and is waiting
+    // for an asynchronous task to complete first.
+    PREF_READ_ERROR_ASYNCHRONOUS_TASK_INCOMPLETE = 10,
+    PREF_READ_ERROR_MAX_ENUM
+  };
+
+  class ReadErrorDelegate {
+   public:
+    virtual ~ReadErrorDelegate() {}
+
+    virtual void OnError(PrefReadError error) = 0;
+  };
+
+  // Whether the store is in a pseudo-read-only mode where changes are not
+  // actually persisted to disk.  This happens in some cases when there are
+  // read errors during startup.
+  virtual bool ReadOnly() const = 0;
+
+  // Gets the read error. Only valid if IsInitializationComplete() returns true.
+  virtual PrefReadError GetReadError() const = 0;
+
+  // Reads the preferences from disk. Notifies observers via
+  // "PrefStore::OnInitializationCompleted" when done.
+  virtual PrefReadError ReadPrefs() = 0;
+
+  // Reads the preferences from disk asynchronously. Notifies observers via
+  // "PrefStore::OnInitializationCompleted" when done. Also it fires
+  // |error_delegate| if it is not NULL and reading error has occurred.
+  // Owns |error_delegate|.
+  virtual void ReadPrefsAsync(ReadErrorDelegate* error_delegate) = 0;
+
+  // Lands any pending writes to disk.
+  virtual void CommitPendingWrite() = 0;
+
+  // Schedule a write if there is any lossy data pending. Unlike
+  // CommitPendingWrite() this does not immediately sync to disk, instead it
+  // triggers an eventual write if there is lossy data pending and if there
+  // isn't one scheduled already.
+  virtual void SchedulePendingLossyWrites() = 0;
+
+ protected:
+  ~PersistentPrefStore() override {}
+};
+
+#endif  // BASE_PREFS_PERSISTENT_PREF_STORE_H_
diff --git a/base/prefs/pref_change_registrar.cc b/components/prefs/pref_change_registrar.cc
similarity index 100%
rename from base/prefs/pref_change_registrar.cc
rename to components/prefs/pref_change_registrar.cc
diff --git a/components/prefs/pref_change_registrar.h b/components/prefs/pref_change_registrar.h
new file mode 100644
index 0000000..cd5a2332
--- /dev/null
+++ b/components/prefs/pref_change_registrar.h
@@ -0,0 +1,81 @@
+// Copyright (c) 2010 The Chromium 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 BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
+#define BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
+
+#include <map>
+#include <string>
+
+#include "base/callback.h"
+#include "base/macros.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_observer.h"
+
+class PrefService;
+
+// Automatically manages the registration of one or more pref change observers
+// with a PrefStore. Functions much like NotificationRegistrar, but specifically
+// manages observers of preference changes. When the Registrar is destroyed,
+// all registered observers are automatically unregistered with the PrefStore.
+class BASE_PREFS_EXPORT PrefChangeRegistrar : public PrefObserver {
+ public:
+  // You can register this type of callback if you need to know the
+  // path of the preference that is changing.
+  typedef base::Callback<void(const std::string&)> NamedChangeCallback;
+
+  PrefChangeRegistrar();
+  virtual ~PrefChangeRegistrar();
+
+  // Must be called before adding or removing observers. Can be called more
+  // than once as long as the value of |service| doesn't change.
+  void Init(PrefService* service);
+
+  // Adds a pref observer for the specified pref |path| and |obs| observer
+  // object. All registered observers will be automatically unregistered
+  // when the registrar's destructor is called.
+  //
+  // The second version binds a callback that will receive the path of
+  // the preference that is changing as its parameter.
+  //
+  // Only one observer may be registered per path.
+  void Add(const std::string& path, const base::Closure& obs);
+  void Add(const std::string& path, const NamedChangeCallback& obs);
+
+  // Removes the pref observer registered for |path|.
+  void Remove(const std::string& path);
+
+  // Removes all observers that have been previously added with a call to Add.
+  void RemoveAll();
+
+  // Returns true if no pref observers are registered.
+  bool IsEmpty() const;
+
+  // Check whether |pref| is in the set of preferences being observed.
+  bool IsObserved(const std::string& pref);
+
+  // Check whether any of the observed preferences has the managed bit set.
+  bool IsManaged();
+
+  // Return the PrefService for this registrar.
+  PrefService* prefs();
+  const PrefService* prefs() const;
+
+ private:
+  // PrefObserver:
+  void OnPreferenceChanged(PrefService* service,
+                           const std::string& pref_name) override;
+
+  static void InvokeUnnamedCallback(const base::Closure& callback,
+                                    const std::string& pref_name);
+
+  typedef std::map<std::string, NamedChangeCallback> ObserverMap;
+
+  ObserverMap observers_;
+  PrefService* service_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefChangeRegistrar);
+};
+
+#endif  // BASE_PREFS_PREF_CHANGE_REGISTRAR_H_
diff --git a/base/prefs/pref_change_registrar_unittest.cc b/components/prefs/pref_change_registrar_unittest.cc
similarity index 100%
rename from base/prefs/pref_change_registrar_unittest.cc
rename to components/prefs/pref_change_registrar_unittest.cc
diff --git a/components/prefs/pref_filter.h b/components/prefs/pref_filter.h
new file mode 100644
index 0000000..82a44c6
--- /dev/null
+++ b/components/prefs/pref_filter.h
@@ -0,0 +1,55 @@
+// Copyright 2013 The Chromium 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 BASE_PREFS_PREF_FILTER_H_
+#define BASE_PREFS_PREF_FILTER_H_
+
+#include <string>
+
+#include "base/callback_forward.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/prefs/base_prefs_export.h"
+
+namespace base {
+class DictionaryValue;
+class Value;
+}  // namespace base
+
+// Filters preferences as they are loaded from disk or updated at runtime.
+// Currently supported only by JsonPrefStore.
+class BASE_PREFS_EXPORT PrefFilter {
+ public:
+  // A callback to be invoked when |prefs| have been read (and possibly
+  // pre-modified) and are now ready to be handed back to this callback's
+  // builder. |schedule_write| indicates whether a write should be immediately
+  // scheduled (typically because the |prefs| were pre-modified).
+  typedef base::Callback<void(scoped_ptr<base::DictionaryValue> prefs,
+                              bool schedule_write)> PostFilterOnLoadCallback;
+
+  virtual ~PrefFilter() {}
+
+  // This method is given ownership of the |pref_store_contents| read from disk
+  // before the underlying PersistentPrefStore gets to use them. It must hand
+  // them back via |post_filter_on_load_callback|, but may modify them first.
+  // Note: This method is asynchronous, which may make calls like
+  // PersistentPrefStore::ReadPrefs() asynchronous. The owner of filtered
+  // PersistentPrefStores should handle this to make the reads look synchronous
+  // to external users (see SegregatedPrefStore::ReadPrefs() for an example).
+  virtual void FilterOnLoad(
+      const PostFilterOnLoadCallback& post_filter_on_load_callback,
+      scoped_ptr<base::DictionaryValue> pref_store_contents) = 0;
+
+  // Receives notification when a pref store value is changed, before Observers
+  // are notified.
+  virtual void FilterUpdate(const std::string& path) = 0;
+
+  // Receives notification when the pref store is about to serialize data
+  // contained in |pref_store_contents| to a string. Modifications to
+  // |pref_store_contents| will be persisted to disk and also affect the
+  // in-memory state.
+  virtual void FilterSerializeData(
+      base::DictionaryValue* pref_store_contents) = 0;
+};
+
+#endif  // BASE_PREFS_PREF_FILTER_H_
diff --git a/base/prefs/pref_member.cc b/components/prefs/pref_member.cc
similarity index 100%
rename from base/prefs/pref_member.cc
rename to components/prefs/pref_member.cc
diff --git a/components/prefs/pref_member.h b/components/prefs/pref_member.h
new file mode 100644
index 0000000..4290c0db
--- /dev/null
+++ b/components/prefs/pref_member.h
@@ -0,0 +1,355 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// A helper class that stays in sync with a preference (bool, int, real,
+// string or filepath).  For example:
+//
+// class MyClass {
+//  public:
+//   MyClass(PrefService* prefs) {
+//     my_string_.Init(prefs::kHomePage, prefs);
+//   }
+//  private:
+//   StringPrefMember my_string_;
+// };
+//
+// my_string_ should stay in sync with the prefs::kHomePage pref and will
+// update if either the pref changes or if my_string_.SetValue is called.
+//
+// An optional observer can be passed into the Init method which can be used to
+// notify MyClass of changes. Note that if you use SetValue(), the observer
+// will not be notified.
+
+#ifndef BASE_PREFS_PREF_MEMBER_H_
+#define BASE_PREFS_PREF_MEMBER_H_
+
+#include <string>
+#include <vector>
+
+#include "base/bind.h"
+#include "base/callback_forward.h"
+#include "base/files/file_path.h"
+#include "base/logging.h"
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_observer.h"
+#include "base/single_thread_task_runner.h"
+#include "base/values.h"
+
+class PrefService;
+
+namespace subtle {
+
+class BASE_PREFS_EXPORT PrefMemberBase : public PrefObserver {
+ public:
+  // Type of callback you can register if you need to know the name of
+  // the pref that is changing.
+  typedef base::Callback<void(const std::string&)> NamedChangeCallback;
+
+  PrefService* prefs() { return prefs_; }
+  const PrefService* prefs() const { return prefs_; }
+
+ protected:
+  class BASE_PREFS_EXPORT Internal
+      : public base::RefCountedThreadSafe<Internal> {
+   public:
+    Internal();
+
+    // Update the value, either by calling |UpdateValueInternal| directly
+    // or by dispatching to the right thread.
+    // Takes ownership of |value|.
+    void UpdateValue(base::Value* value,
+                     bool is_managed,
+                     bool is_user_modifiable,
+                     const base::Closure& callback) const;
+
+    void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner);
+
+    // See PrefMember<> for description.
+    bool IsManaged() const {
+      return is_managed_;
+    }
+
+    bool IsUserModifiable() const {
+      return is_user_modifiable_;
+    }
+
+   protected:
+    friend class base::RefCountedThreadSafe<Internal>;
+    virtual ~Internal();
+
+    void CheckOnCorrectThread() const {
+      DCHECK(IsOnCorrectThread());
+    }
+
+   private:
+    // This method actually updates the value. It should only be called from
+    // the thread the PrefMember is on.
+    virtual bool UpdateValueInternal(const base::Value& value) const = 0;
+
+    bool IsOnCorrectThread() const;
+
+    scoped_refptr<base::SingleThreadTaskRunner> thread_task_runner_;
+    mutable bool is_managed_;
+    mutable bool is_user_modifiable_;
+
+    DISALLOW_COPY_AND_ASSIGN(Internal);
+  };
+
+  PrefMemberBase();
+  virtual ~PrefMemberBase();
+
+  // See PrefMember<> for description.
+  void Init(const std::string& pref_name,
+            PrefService* prefs,
+            const NamedChangeCallback& observer);
+  void Init(const std::string& pref_name, PrefService* prefs);
+
+  virtual void CreateInternal() const = 0;
+
+  // See PrefMember<> for description.
+  void Destroy();
+
+  void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner);
+
+  // PrefObserver
+  void OnPreferenceChanged(PrefService* service,
+                           const std::string& pref_name) override;
+
+  void VerifyValuePrefName() const {
+    DCHECK(!pref_name_.empty());
+  }
+
+  // This method is used to do the actual sync with the preference.
+  // Note: it is logically const, because it doesn't modify the state
+  // seen by the outside world. It is just doing a lazy load behind the scenes.
+  void UpdateValueFromPref(const base::Closure& callback) const;
+
+  // Verifies the preference name, and lazily loads the preference value if
+  // it hasn't been loaded yet.
+  void VerifyPref() const;
+
+  const std::string& pref_name() const { return pref_name_; }
+
+  virtual Internal* internal() const = 0;
+
+  // Used to allow registering plain base::Closure callbacks.
+  static void InvokeUnnamedCallback(const base::Closure& callback,
+                                    const std::string& pref_name);
+
+ private:
+  // Ordered the members to compact the class instance.
+  std::string pref_name_;
+  NamedChangeCallback observer_;
+  PrefService* prefs_;
+
+ protected:
+  bool setting_value_;
+};
+
+// This function implements StringListPrefMember::UpdateValue().
+// It is exposed here for testing purposes.
+bool BASE_PREFS_EXPORT PrefMemberVectorStringUpdate(
+    const base::Value& value,
+    std::vector<std::string>* string_vector);
+
+}  // namespace subtle
+
+template <typename ValueType>
+class PrefMember : public subtle::PrefMemberBase {
+ public:
+  // Defer initialization to an Init method so it's easy to make this class be
+  // a member variable.
+  PrefMember() {}
+  virtual ~PrefMember() {}
+
+  // Do the actual initialization of the class.  Use the two-parameter
+  // version if you don't want any notifications of changes.  This
+  // method should only be called on the UI thread.
+  void Init(const std::string& pref_name,
+            PrefService* prefs,
+            const NamedChangeCallback& observer) {
+    subtle::PrefMemberBase::Init(pref_name, prefs, observer);
+  }
+  void Init(const std::string& pref_name,
+            PrefService* prefs,
+            const base::Closure& observer) {
+    subtle::PrefMemberBase::Init(
+        pref_name, prefs,
+        base::Bind(&PrefMemberBase::InvokeUnnamedCallback, observer));
+  }
+  void Init(const std::string& pref_name, PrefService* prefs) {
+    subtle::PrefMemberBase::Init(pref_name, prefs);
+  }
+
+  // Unsubscribes the PrefMember from the PrefService. After calling this
+  // function, the PrefMember may not be used any more on the UI thread.
+  // Assuming |MoveToThread| was previously called, |GetValue|, |IsManaged|,
+  // and |IsUserModifiable| can still be called from the other thread but
+  // the results will no longer update from the PrefService.
+  // This method should only be called on the UI thread.
+  void Destroy() {
+    subtle::PrefMemberBase::Destroy();
+  }
+
+  // Moves the PrefMember to another thread, allowing read accesses from there.
+  // Changes from the PrefService will be propagated asynchronously
+  // via PostTask.
+  // This method should only be used from the thread the PrefMember is currently
+  // on, which is the UI thread by default.
+  void MoveToThread(scoped_refptr<base::SingleThreadTaskRunner> task_runner) {
+    subtle::PrefMemberBase::MoveToThread(task_runner);
+  }
+
+  // Check whether the pref is managed, i.e. controlled externally through
+  // enterprise configuration management (e.g. windows group policy). Returns
+  // false for unknown prefs.
+  // This method should only be used from the thread the PrefMember is currently
+  // on, which is the UI thread unless changed by |MoveToThread|.
+  bool IsManaged() const {
+    VerifyPref();
+    return internal_->IsManaged();
+  }
+
+  // Checks whether the pref can be modified by the user. This returns false
+  // when the pref is managed by a policy or an extension, and when a command
+  // line flag overrides the pref.
+  // This method should only be used from the thread the PrefMember is currently
+  // on, which is the UI thread unless changed by |MoveToThread|.
+  bool IsUserModifiable() const {
+    VerifyPref();
+    return internal_->IsUserModifiable();
+  }
+
+  // Retrieve the value of the member variable.
+  // This method should only be used from the thread the PrefMember is currently
+  // on, which is the UI thread unless changed by |MoveToThread|.
+  ValueType GetValue() const {
+    VerifyPref();
+    return internal_->value();
+  }
+
+  // Provided as a convenience.
+  ValueType operator*() const {
+    return GetValue();
+  }
+
+  // Set the value of the member variable.
+  // This method should only be called on the UI thread.
+  void SetValue(const ValueType& value) {
+    VerifyValuePrefName();
+    setting_value_ = true;
+    UpdatePref(value);
+    setting_value_ = false;
+  }
+
+  // Returns the pref name.
+  const std::string& GetPrefName() const {
+    return pref_name();
+  }
+
+ private:
+  class Internal : public subtle::PrefMemberBase::Internal {
+   public:
+    Internal() : value_(ValueType()) {}
+
+    ValueType value() {
+      CheckOnCorrectThread();
+      return value_;
+    }
+
+   protected:
+    ~Internal() override {}
+
+    BASE_PREFS_EXPORT bool UpdateValueInternal(
+        const base::Value& value) const override;
+
+    // We cache the value of the pref so we don't have to keep walking the pref
+    // tree.
+    mutable ValueType value_;
+
+   private:
+    DISALLOW_COPY_AND_ASSIGN(Internal);
+  };
+
+  Internal* internal() const override { return internal_.get(); }
+  void CreateInternal() const override { internal_ = new Internal(); }
+
+  // This method is used to do the actual sync with pref of the specified type.
+  void BASE_PREFS_EXPORT UpdatePref(const ValueType& value);
+
+  mutable scoped_refptr<Internal> internal_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefMember);
+};
+
+// Declaration of template specialization need to be repeated here
+// specifically for each specialization (rather than just once above)
+// or at least one of our compilers won't be happy in all cases.
+// Specifically, it was failing on ChromeOS with a complaint about
+// PrefMember<FilePath>::UpdateValueInternal not being defined when
+// built in a chroot with the following parameters:
+//
+// FEATURES="noclean nostrip" USE="-chrome_debug -chrome_remoting
+// -chrome_internal -chrome_pdf component_build"
+// ~/trunk/goma/goma-wrapper cros_chrome_make --board=${BOARD}
+// --install --runhooks
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<bool>::UpdatePref(const bool& value);
+
+template <>
+BASE_PREFS_EXPORT bool PrefMember<bool>::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<int>::UpdatePref(const int& value);
+
+template <>
+BASE_PREFS_EXPORT bool PrefMember<int>::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<double>::UpdatePref(const double& value);
+
+template <>
+BASE_PREFS_EXPORT bool PrefMember<double>::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<std::string>::UpdatePref(
+    const std::string& value);
+
+template <>
+BASE_PREFS_EXPORT bool PrefMember<std::string>::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<base::FilePath>::UpdatePref(
+    const base::FilePath& value);
+
+template <>
+BASE_PREFS_EXPORT bool
+PrefMember<base::FilePath>::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+template <>
+BASE_PREFS_EXPORT void PrefMember<std::vector<std::string> >::UpdatePref(
+    const std::vector<std::string>& value);
+
+template <>
+BASE_PREFS_EXPORT bool
+PrefMember<std::vector<std::string> >::Internal::UpdateValueInternal(
+    const base::Value& value) const;
+
+typedef PrefMember<bool> BooleanPrefMember;
+typedef PrefMember<int> IntegerPrefMember;
+typedef PrefMember<double> DoublePrefMember;
+typedef PrefMember<std::string> StringPrefMember;
+typedef PrefMember<base::FilePath> FilePathPrefMember;
+// This preference member is expensive for large string arrays.
+typedef PrefMember<std::vector<std::string> > StringListPrefMember;
+
+#endif  // BASE_PREFS_PREF_MEMBER_H_
diff --git a/base/prefs/pref_member_unittest.cc b/components/prefs/pref_member_unittest.cc
similarity index 100%
rename from base/prefs/pref_member_unittest.cc
rename to components/prefs/pref_member_unittest.cc
diff --git a/components/prefs/pref_notifier.h b/components/prefs/pref_notifier.h
new file mode 100644
index 0000000..e0df260c
--- /dev/null
+++ b/components/prefs/pref_notifier.h
@@ -0,0 +1,26 @@
+// Copyright (c) 2011 The Chromium 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 BASE_PREFS_PREF_NOTIFIER_H_
+#define BASE_PREFS_PREF_NOTIFIER_H_
+
+#include <string>
+
+// Delegate interface used by PrefValueStore to notify its owner about changes
+// to the preference values.
+// TODO(mnissler, danno): Move this declaration to pref_value_store.h once we've
+// cleaned up all public uses of this interface.
+class PrefNotifier {
+ public:
+  virtual ~PrefNotifier() {}
+
+  // Sends out a change notification for the preference identified by
+  // |pref_name|.
+  virtual void OnPreferenceChanged(const std::string& pref_name) = 0;
+
+  // Broadcasts the intialization completed notification.
+  virtual void OnInitializationCompleted(bool succeeded) = 0;
+};
+
+#endif  // BASE_PREFS_PREF_NOTIFIER_H_
diff --git a/base/prefs/pref_notifier_impl.cc b/components/prefs/pref_notifier_impl.cc
similarity index 100%
rename from base/prefs/pref_notifier_impl.cc
rename to components/prefs/pref_notifier_impl.cc
diff --git a/components/prefs/pref_notifier_impl.h b/components/prefs/pref_notifier_impl.h
new file mode 100644
index 0000000..6e62e232
--- /dev/null
+++ b/components/prefs/pref_notifier_impl.h
@@ -0,0 +1,74 @@
+// Copyright (c) 2011 The Chromium 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 BASE_PREFS_PREF_NOTIFIER_IMPL_H_
+#define BASE_PREFS_PREF_NOTIFIER_IMPL_H_
+
+#include <list>
+#include <string>
+
+#include "base/callback.h"
+#include "base/compiler_specific.h"
+#include "base/containers/hash_tables.h"
+#include "base/macros.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_notifier.h"
+#include "base/prefs/pref_observer.h"
+#include "base/threading/thread_checker.h"
+
+class PrefService;
+
+// The PrefNotifier implementation used by the PrefService.
+class BASE_PREFS_EXPORT PrefNotifierImpl
+    : public NON_EXPORTED_BASE(PrefNotifier) {
+ public:
+  PrefNotifierImpl();
+  explicit PrefNotifierImpl(PrefService* pref_service);
+  ~PrefNotifierImpl() override;
+
+  // If the pref at the given path changes, we call the observer's
+  // OnPreferenceChanged method.
+  void AddPrefObserver(const std::string& path, PrefObserver* observer);
+  void RemovePrefObserver(const std::string& path, PrefObserver* observer);
+
+  // We run the callback once, when initialization completes. The bool
+  // parameter will be set to true for successful initialization,
+  // false for unsuccessful.
+  void AddInitObserver(base::Callback<void(bool)> observer);
+
+  void SetPrefService(PrefService* pref_service);
+
+ protected:
+  // PrefNotifier overrides.
+  void OnPreferenceChanged(const std::string& pref_name) override;
+  void OnInitializationCompleted(bool succeeded) override;
+
+  // A map from pref names to a list of observers. Observers get fired in the
+  // order they are added. These should only be accessed externally for unit
+  // testing.
+  typedef base::ObserverList<PrefObserver> PrefObserverList;
+  typedef base::hash_map<std::string, PrefObserverList*> PrefObserverMap;
+
+  typedef std::list<base::Callback<void(bool)>> PrefInitObserverList;
+
+  const PrefObserverMap* pref_observers() const { return &pref_observers_; }
+
+ private:
+  // For the given pref_name, fire any observer of the pref. Virtual so it can
+  // be mocked for unit testing.
+  virtual void FireObservers(const std::string& path);
+
+  // Weak reference; the notifier is owned by the PrefService.
+  PrefService* pref_service_;
+
+  PrefObserverMap pref_observers_;
+  PrefInitObserverList init_observers_;
+
+  base::ThreadChecker thread_checker_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefNotifierImpl);
+};
+
+#endif  // BASE_PREFS_PREF_NOTIFIER_IMPL_H_
diff --git a/base/prefs/pref_notifier_impl_unittest.cc b/components/prefs/pref_notifier_impl_unittest.cc
similarity index 100%
rename from base/prefs/pref_notifier_impl_unittest.cc
rename to components/prefs/pref_notifier_impl_unittest.cc
diff --git a/components/prefs/pref_observer.h b/components/prefs/pref_observer.h
new file mode 100644
index 0000000..5d8f5b63
--- /dev/null
+++ b/components/prefs/pref_observer.h
@@ -0,0 +1,21 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PREF_OBSERVER_H_
+#define BASE_PREFS_PREF_OBSERVER_H_
+
+#include <string>
+
+class PrefService;
+
+// Used internally to the Prefs subsystem to pass preference change
+// notifications between PrefService, PrefNotifierImpl and
+// PrefChangeRegistrar.
+class PrefObserver {
+ public:
+  virtual void OnPreferenceChanged(PrefService* service,
+                                   const std::string& pref_name) = 0;
+};
+
+#endif  // BASE_PREFS_PREF_OBSERVER_H_
diff --git a/base/prefs/pref_registry.cc b/components/prefs/pref_registry.cc
similarity index 100%
rename from base/prefs/pref_registry.cc
rename to components/prefs/pref_registry.cc
diff --git a/components/prefs/pref_registry.h b/components/prefs/pref_registry.h
new file mode 100644
index 0000000..7e141d8
--- /dev/null
+++ b/components/prefs/pref_registry.h
@@ -0,0 +1,89 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PREF_REGISTRY_H_
+#define BASE_PREFS_PREF_REGISTRY_H_
+
+#include <stdint.h>
+
+#include "base/containers/hash_tables.h"
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_value_map.h"
+
+namespace base {
+class Value;
+}
+
+class DefaultPrefStore;
+class PrefStore;
+
+// Preferences need to be registered with a type and default value
+// before they are used.
+//
+// The way you use a PrefRegistry is that you register all required
+// preferences on it (via one of its subclasses), then pass it as a
+// construction parameter to PrefService.
+//
+// Currently, registrations after constructing the PrefService will
+// also work, but this is being deprecated.
+class BASE_PREFS_EXPORT PrefRegistry : public base::RefCounted<PrefRegistry> {
+ public:
+  // Registration flags that can be specified which impact how the pref will
+  // behave or be stored. This will be passed in a bitmask when the pref is
+  // registered. Subclasses of PrefRegistry can specify their own flags. Care
+  // must be taken to ensure none of these overlap with the flags below.
+  enum PrefRegistrationFlags : uint32_t {
+    // No flags are specified.
+    NO_REGISTRATION_FLAGS = 0,
+
+    // The first 8 bits are reserved for subclasses of PrefRegistry to use.
+
+    // This marks the pref as "lossy". There is no strict time guarantee on when
+    // a lossy pref will be persisted to permanent storage when it is modified.
+    LOSSY_PREF = 1 << 8,
+  };
+
+  typedef PrefValueMap::const_iterator const_iterator;
+  typedef base::hash_map<std::string, uint32_t> PrefRegistrationFlagsMap;
+
+  PrefRegistry();
+
+  // Retrieve the set of registration flags for the given preference. The return
+  // value is a bitmask of PrefRegistrationFlags.
+  uint32_t GetRegistrationFlags(const std::string& pref_name) const;
+
+  // Gets the registered defaults.
+  scoped_refptr<PrefStore> defaults();
+
+  // Allows iteration over defaults.
+  const_iterator begin() const;
+  const_iterator end() const;
+
+  // Changes the default value for a preference. Takes ownership of |value|.
+  //
+  // |pref_name| must be a previously registered preference.
+  void SetDefaultPrefValue(const std::string& pref_name, base::Value* value);
+
+ protected:
+  friend class base::RefCounted<PrefRegistry>;
+  virtual ~PrefRegistry();
+
+  // Used by subclasses to register a default value and registration flags for
+  // a preference. |flags| is a bitmask of |PrefRegistrationFlags|.
+  void RegisterPreference(const std::string& path,
+                          base::Value* default_value,
+                          uint32_t flags);
+
+  scoped_refptr<DefaultPrefStore> defaults_;
+
+  // A map of pref name to a bitmask of PrefRegistrationFlags.
+  PrefRegistrationFlagsMap registration_flags_;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(PrefRegistry);
+};
+
+#endif  // BASE_PREFS_PREF_REGISTRY_H_
diff --git a/base/prefs/pref_registry_simple.cc b/components/prefs/pref_registry_simple.cc
similarity index 100%
rename from base/prefs/pref_registry_simple.cc
rename to components/prefs/pref_registry_simple.cc
diff --git a/components/prefs/pref_registry_simple.h b/components/prefs/pref_registry_simple.h
new file mode 100644
index 0000000..6afc012b
--- /dev/null
+++ b/components/prefs/pref_registry_simple.h
@@ -0,0 +1,91 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
+#define BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
+
+#include <stdint.h>
+
+#include <string>
+
+#include "base/macros.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_registry.h"
+
+namespace base {
+class DictionaryValue;
+class FilePath;
+class ListValue;
+}
+
+// A simple implementation of PrefRegistry.
+class BASE_PREFS_EXPORT PrefRegistrySimple : public PrefRegistry {
+ public:
+  PrefRegistrySimple();
+
+  void RegisterBooleanPref(const std::string& path, bool default_value);
+  void RegisterIntegerPref(const std::string& path, int default_value);
+  void RegisterDoublePref(const std::string& path, double default_value);
+  void RegisterStringPref(const std::string& path,
+                          const std::string& default_value);
+  void RegisterFilePathPref(const std::string& path,
+                            const base::FilePath& default_value);
+  void RegisterListPref(const std::string& path);
+  void RegisterDictionaryPref(const std::string& path);
+  void RegisterListPref(const std::string& path,
+                        base::ListValue* default_value);
+  void RegisterDictionaryPref(const std::string& path,
+                              base::DictionaryValue* default_value);
+  void RegisterInt64Pref(const std::string& path, int64_t default_value);
+  void RegisterUint64Pref(const std::string&, uint64_t default_value);
+
+  // Versions of registration functions that accept PrefRegistrationFlags.
+  // |flags| is a bitmask of PrefRegistrationFlags.
+  void RegisterBooleanPref(const std::string&,
+                           bool default_value,
+                           uint32_t flags);
+  void RegisterIntegerPref(const std::string&,
+                           int default_value,
+                           uint32_t flags);
+  void RegisterDoublePref(const std::string&,
+                          double default_value,
+                          uint32_t flags);
+  void RegisterStringPref(const std::string&,
+                          const std::string& default_value,
+                          uint32_t flags);
+  void RegisterFilePathPref(const std::string&,
+                            const base::FilePath& default_value,
+                            uint32_t flags);
+  void RegisterListPref(const std::string&, uint32_t flags);
+  void RegisterDictionaryPref(const std::string&, uint32_t flags);
+  void RegisterListPref(const std::string&,
+                        base::ListValue* default_value,
+                        uint32_t flags);
+  void RegisterDictionaryPref(const std::string&,
+                              base::DictionaryValue* default_value,
+                              uint32_t flags);
+  void RegisterInt64Pref(const std::string&,
+                         int64_t default_value,
+                         uint32_t flags);
+  void RegisterUint64Pref(const std::string&,
+                          uint64_t default_value,
+                          uint32_t flags);
+
+ protected:
+  ~PrefRegistrySimple() override;
+
+  // Allows subclasses to hook into pref registration.
+  virtual void OnPrefRegistered(const std::string&,
+                                base::Value* default_value,
+                                uint32_t flags);
+
+ private:
+  void RegisterPrefAndNotify(const std::string&,
+                             base::Value* default_value,
+                             uint32_t flags);
+
+  DISALLOW_COPY_AND_ASSIGN(PrefRegistrySimple);
+};
+
+#endif  // BASE_PREFS_PREF_REGISTRY_SIMPLE_H_
diff --git a/base/prefs/pref_service.cc b/components/prefs/pref_service.cc
similarity index 100%
rename from base/prefs/pref_service.cc
rename to components/prefs/pref_service.cc
diff --git a/components/prefs/pref_service.h b/components/prefs/pref_service.h
new file mode 100644
index 0000000..bec7830
--- /dev/null
+++ b/components/prefs/pref_service.h
@@ -0,0 +1,385 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This provides a way to access the application's current preferences.
+
+// Chromium settings and storage represent user-selected preferences and
+// information and MUST not be extracted, overwritten or modified except
+// through Chromium defined APIs.
+
+#ifndef BASE_PREFS_PREF_SERVICE_H_
+#define BASE_PREFS_PREF_SERVICE_H_
+
+#include <stdint.h>
+
+#include <set>
+#include <string>
+
+#include "base/callback.h"
+#include "base/compiler_specific.h"
+#include "base/containers/hash_tables.h"
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/persistent_pref_store.h"
+#include "base/threading/non_thread_safe.h"
+#include "base/values.h"
+
+class PrefNotifier;
+class PrefNotifierImpl;
+class PrefObserver;
+class PrefRegistry;
+class PrefValueStore;
+class PrefStore;
+
+namespace base {
+class FilePath;
+}
+
+namespace subtle {
+class PrefMemberBase;
+class ScopedUserPrefUpdateBase;
+}
+
+// Base class for PrefServices. You can use the base class to read and
+// interact with preferences, but not to register new preferences; for
+// that see e.g. PrefRegistrySimple.
+//
+// Settings and storage accessed through this class represent
+// user-selected preferences and information and MUST not be
+// extracted, overwritten or modified except through the defined APIs.
+class BASE_PREFS_EXPORT PrefService : public base::NonThreadSafe {
+ public:
+  enum PrefInitializationStatus {
+    INITIALIZATION_STATUS_WAITING,
+    INITIALIZATION_STATUS_SUCCESS,
+    INITIALIZATION_STATUS_CREATED_NEW_PREF_STORE,
+    INITIALIZATION_STATUS_ERROR
+  };
+
+  // A helper class to store all the information associated with a preference.
+  class BASE_PREFS_EXPORT Preference {
+   public:
+    // The type of the preference is determined by the type with which it is
+    // registered. This type needs to be a boolean, integer, double, string,
+    // dictionary (a branch), or list.  You shouldn't need to construct this on
+    // your own; use the PrefService::Register*Pref methods instead.
+    Preference(const PrefService* service,
+               const std::string& name,
+               base::Value::Type type);
+    ~Preference() {}
+
+    // Returns the name of the Preference (i.e., the key, e.g.,
+    // browser.window_placement).
+    const std::string name() const;
+
+    // Returns the registered type of the preference.
+    base::Value::Type GetType() const;
+
+    // Returns the value of the Preference, falling back to the registered
+    // default value if no other has been set.
+    const base::Value* GetValue() const;
+
+    // Returns the value recommended by the admin, if any.
+    const base::Value* GetRecommendedValue() const;
+
+    // Returns true if the Preference is managed, i.e. set by an admin policy.
+    // Since managed prefs have the highest priority, this also indicates
+    // whether the pref is actually being controlled by the policy setting.
+    bool IsManaged() const;
+
+    // Returns true if the Preference is controlled by the custodian of the
+    // supervised user. Since a supervised user is not expected to have an admin
+    // policy, this is the controlling pref if set.
+    bool IsManagedByCustodian() const;
+
+    // Returns true if the Preference is recommended, i.e. set by an admin
+    // policy but the user is allowed to change it.
+    bool IsRecommended() const;
+
+    // Returns true if the Preference has a value set by an extension, even if
+    // that value is being overridden by a higher-priority source.
+    bool HasExtensionSetting() const;
+
+    // Returns true if the Preference has a user setting, even if that value is
+    // being overridden by a higher-priority source.
+    bool HasUserSetting() const;
+
+    // Returns true if the Preference value is currently being controlled by an
+    // extension, and not by any higher-priority source.
+    bool IsExtensionControlled() const;
+
+    // Returns true if the Preference value is currently being controlled by a
+    // user setting, and not by any higher-priority source.
+    bool IsUserControlled() const;
+
+    // Returns true if the Preference is currently using its default value,
+    // and has not been set by any higher-priority source (even with the same
+    // value).
+    bool IsDefaultValue() const;
+
+    // Returns true if the user can change the Preference value, which is the
+    // case if no higher-priority source than the user store controls the
+    // Preference.
+    bool IsUserModifiable() const;
+
+    // Returns true if an extension can change the Preference value, which is
+    // the case if no higher-priority source than the extension store controls
+    // the Preference.
+    bool IsExtensionModifiable() const;
+
+    // Return the registration flags for this pref as a bitmask of
+    // PrefRegistry::PrefRegistrationFlags.
+    uint32_t registration_flags() const { return registration_flags_; }
+
+   private:
+    friend class PrefService;
+
+    PrefValueStore* pref_value_store() const {
+      return pref_service_->pref_value_store_.get();
+    }
+
+    const std::string name_;
+
+    const base::Value::Type type_;
+
+    uint32_t registration_flags_;
+
+    // Reference to the PrefService in which this pref was created.
+    const PrefService* pref_service_;
+  };
+
+  // You may wish to use PrefServiceFactory or one of its subclasses
+  // for simplified construction.
+  PrefService(
+      PrefNotifierImpl* pref_notifier,
+      PrefValueStore* pref_value_store,
+      PersistentPrefStore* user_prefs,
+      PrefRegistry* pref_registry,
+      base::Callback<void(PersistentPrefStore::PrefReadError)>
+          read_error_callback,
+      bool async);
+  virtual ~PrefService();
+
+  // Lands pending writes to disk. This should only be used if we need to save
+  // immediately (basically, during shutdown).
+  void CommitPendingWrite();
+
+  // Schedule a write if there is any lossy data pending. Unlike
+  // CommitPendingWrite() this does not immediately sync to disk, instead it
+  // triggers an eventual write if there is lossy data pending and if there
+  // isn't one scheduled already.
+  void SchedulePendingLossyWrites();
+
+  // Returns true if the preference for the given preference name is available
+  // and is managed.
+  bool IsManagedPreference(const std::string& pref_name) const;
+
+  // Returns true if the preference for the given preference name is available
+  // and is controlled by the parent/guardian of the child Account.
+  bool IsPreferenceManagedByCustodian(const std::string& pref_name) const;
+
+  // Returns |true| if a preference with the given name is available and its
+  // value can be changed by the user.
+  bool IsUserModifiablePreference(const std::string& pref_name) const;
+
+  // Look up a preference.  Returns NULL if the preference is not
+  // registered.
+  const PrefService::Preference* FindPreference(const std::string& path) const;
+
+  // If the path is valid and the value at the end of the path matches the type
+  // specified, it will return the specified value.  Otherwise, the default
+  // value (set when the pref was registered) will be returned.
+  bool GetBoolean(const std::string& path) const;
+  int GetInteger(const std::string& path) const;
+  double GetDouble(const std::string& path) const;
+  std::string GetString(const std::string& path) const;
+  base::FilePath GetFilePath(const std::string& path) const;
+
+  // Returns the branch if it exists, or the registered default value otherwise.
+  // Note that |path| must point to a registered preference. In that case, these
+  // functions will never return NULL.
+  const base::DictionaryValue* GetDictionary(const std::string& path) const;
+  const base::ListValue* GetList(const std::string& path) const;
+
+  // Removes a user pref and restores the pref to its default value.
+  void ClearPref(const std::string& path);
+
+  // If the path is valid (i.e., registered), update the pref value in the user
+  // prefs.
+  // To set the value of dictionary or list values in the pref tree use
+  // Set(), but to modify the value of a dictionary or list use either
+  // ListPrefUpdate or DictionaryPrefUpdate from scoped_user_pref_update.h.
+  void Set(const std::string& path, const base::Value& value);
+  void SetBoolean(const std::string& path, bool value);
+  void SetInteger(const std::string& path, int value);
+  void SetDouble(const std::string& path, double value);
+  void SetString(const std::string& path, const std::string& value);
+  void SetFilePath(const std::string& path, const base::FilePath& value);
+
+  // Int64 helper methods that actually store the given value as a string.
+  // Note that if obtaining the named value via GetDictionary or GetList, the
+  // Value type will be TYPE_STRING.
+  void SetInt64(const std::string& path, int64_t value);
+  int64_t GetInt64(const std::string& path) const;
+
+  // As above, but for unsigned values.
+  void SetUint64(const std::string& path, uint64_t value);
+  uint64_t GetUint64(const std::string& path) const;
+
+  // Returns the value of the given preference, from the user pref store. If
+  // the preference is not set in the user pref store, returns NULL.
+  const base::Value* GetUserPrefValue(const std::string& path) const;
+
+  // Changes the default value for a preference. Takes ownership of |value|.
+  //
+  // Will cause a pref change notification to be fired if this causes
+  // the effective value to change.
+  void SetDefaultPrefValue(const std::string& path, base::Value* value);
+
+  // Returns the default value of the given preference. |path| must point to a
+  // registered preference. In that case, will never return NULL.
+  const base::Value* GetDefaultPrefValue(const std::string& path) const;
+
+  // Returns true if a value has been set for the specified path.
+  // NOTE: this is NOT the same as FindPreference. In particular
+  // FindPreference returns whether RegisterXXX has been invoked, where as
+  // this checks if a value exists for the path.
+  bool HasPrefPath(const std::string& path) const;
+
+  // Returns a dictionary with effective preference values.
+  scoped_ptr<base::DictionaryValue> GetPreferenceValues() const;
+
+  // Returns a dictionary with effective preference values, omitting prefs that
+  // are at their default values.
+  scoped_ptr<base::DictionaryValue> GetPreferenceValuesOmitDefaults() const;
+
+  // Returns a dictionary with effective preference values. Contrary to
+  // GetPreferenceValues(), the paths of registered preferences are not split on
+  // '.' characters. If a registered preference stores a dictionary, however,
+  // the hierarchical structure inside the preference will be preserved.
+  // For example, if "foo.bar" is a registered preference, the result could look
+  // like this:
+  //   {"foo.bar": {"a": {"b": true}}}.
+  scoped_ptr<base::DictionaryValue> GetPreferenceValuesWithoutPathExpansion()
+      const;
+
+  bool ReadOnly() const;
+
+  PrefInitializationStatus GetInitializationStatus() const;
+
+  // Tell our PrefValueStore to update itself to |command_line_store|.
+  // Takes ownership of the store.
+  virtual void UpdateCommandLinePrefStore(PrefStore* command_line_store);
+
+  // We run the callback once, when initialization completes. The bool
+  // parameter will be set to true for successful initialization,
+  // false for unsuccessful.
+  void AddPrefInitObserver(base::Callback<void(bool)> callback);
+
+  // Returns the PrefRegistry object for this service. You should not
+  // use this; the intent is for no registrations to take place after
+  // PrefService has been constructed.
+  //
+  // Instead of using this method, the recommended approach is to
+  // register all preferences for a class Xyz up front in a static
+  // Xyz::RegisterPrefs function, which gets invoked early in the
+  // application's start-up, before a PrefService is created.
+  //
+  // As an example, prefs registration in Chrome is triggered by the
+  // functions chrome::RegisterPrefs (for global preferences) and
+  // chrome::RegisterProfilePrefs (for user-specific preferences)
+  // implemented in chrome/browser/prefs/browser_prefs.cc.
+  PrefRegistry* DeprecatedGetPrefRegistry();
+
+ protected:
+  // The PrefNotifier handles registering and notifying preference observers.
+  // It is created and owned by this PrefService. Subclasses may access it for
+  // unit testing.
+  scoped_ptr<PrefNotifierImpl> pref_notifier_;
+
+  // The PrefValueStore provides prioritized preference values. It is owned by
+  // this PrefService. Subclasses may access it for unit testing.
+  scoped_ptr<PrefValueStore> pref_value_store_;
+
+  scoped_refptr<PrefRegistry> pref_registry_;
+
+  // Pref Stores and profile that we passed to the PrefValueStore.
+  scoped_refptr<PersistentPrefStore> user_pref_store_;
+
+  // Callback to call when a read error occurs.
+  base::Callback<void(PersistentPrefStore::PrefReadError)> read_error_callback_;
+
+ private:
+  // Hash map expected to be fastest here since it minimises expensive
+  // string comparisons. Order is unimportant, and deletions are rare.
+  // Confirmed on Android where this speeded Chrome startup by roughly 50ms
+  // vs. std::map, and by roughly 180ms vs. std::set of Preference pointers.
+  typedef base::hash_map<std::string, Preference> PreferenceMap;
+
+  // Give access to ReportUserPrefChanged() and GetMutableUserPref().
+  friend class subtle::ScopedUserPrefUpdateBase;
+  friend class PrefServiceTest_WriteablePrefStoreFlags_Test;
+
+  // Registration of pref change observers must be done using the
+  // PrefChangeRegistrar, which is declared as a friend here to grant it
+  // access to the otherwise protected members Add/RemovePrefObserver.
+  // PrefMember registers for preferences changes notification directly to
+  // avoid the storage overhead of the registrar, so its base class must be
+  // declared as a friend, too.
+  friend class PrefChangeRegistrar;
+  friend class subtle::PrefMemberBase;
+
+  // These are protected so they can only be accessed by the friend
+  // classes listed above.
+  //
+  // If the pref at the given path changes, we call the observer's
+  // OnPreferenceChanged method. Note that observers should not call
+  // these methods directly but rather use a PrefChangeRegistrar to
+  // make sure the observer gets cleaned up properly.
+  //
+  // Virtual for testing.
+  virtual void AddPrefObserver(const std::string& path, PrefObserver* obs);
+  virtual void RemovePrefObserver(const std::string& path, PrefObserver* obs);
+
+  // Sends notification of a changed preference. This needs to be called by
+  // a ScopedUserPrefUpdate if a DictionaryValue or ListValue is changed.
+  void ReportUserPrefChanged(const std::string& key);
+
+  // Sets the value for this pref path in the user pref store and informs the
+  // PrefNotifier of the change.
+  void SetUserPrefValue(const std::string& path, base::Value* new_value);
+
+  // Load preferences from storage, attempting to diagnose and handle errors.
+  // This should only be called from the constructor.
+  void InitFromStorage(bool async);
+
+  // Used to set the value of dictionary or list values in the user pref store.
+  // This will create a dictionary or list if one does not exist in the user
+  // pref store. This method returns NULL only if you're requesting an
+  // unregistered pref or a non-dict/non-list pref.
+  // |type| may only be Values::TYPE_DICTIONARY or Values::TYPE_LIST and
+  // |path| must point to a registered preference of type |type|.
+  // Ownership of the returned value remains at the user pref store.
+  base::Value* GetMutableUserPref(const std::string& path,
+                                  base::Value::Type type);
+
+  // GetPreferenceValue is the equivalent of FindPreference(path)->GetValue(),
+  // it has been added for performance. If is faster because it does
+  // not need to find or create a Preference object to get the
+  // value (GetValue() calls back though the preference service to
+  // actually get the value.).
+  const base::Value* GetPreferenceValue(const std::string& path) const;
+
+  // Local cache of registered Preference objects. The pref_registry_
+  // is authoritative with respect to what the types and default values
+  // of registered preferences are.
+  mutable PreferenceMap prefs_map_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefService);
+};
+
+#endif  // BASE_PREFS_PREF_SERVICE_H_
diff --git a/base/prefs/pref_service_factory.cc b/components/prefs/pref_service_factory.cc
similarity index 100%
rename from base/prefs/pref_service_factory.cc
rename to components/prefs/pref_service_factory.cc
diff --git a/components/prefs/pref_service_factory.h b/components/prefs/pref_service_factory.h
new file mode 100644
index 0000000..f84e037
--- /dev/null
+++ b/components/prefs/pref_service_factory.h
@@ -0,0 +1,91 @@
+// Copyright 2013 The Chromium 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 BASE_PREFS_PREF_SERVICE_FACTORY_H_
+#define BASE_PREFS_PREF_SERVICE_FACTORY_H_
+
+#include "base/callback.h"
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/persistent_pref_store.h"
+#include "base/prefs/pref_registry.h"
+#include "base/prefs/pref_store.h"
+
+class PrefService;
+
+namespace base {
+
+class FilePath;
+class SequencedTaskRunner;
+
+// A class that allows convenient building of PrefService.
+class BASE_PREFS_EXPORT PrefServiceFactory {
+ public:
+  PrefServiceFactory();
+  virtual ~PrefServiceFactory();
+
+  // Functions for setting the various parameters of the PrefService to build.
+  void set_managed_prefs(const scoped_refptr<PrefStore>& managed_prefs) {
+    managed_prefs_ = managed_prefs;
+  }
+  void set_supervised_user_prefs(
+      const scoped_refptr<PrefStore>& supervised_user_prefs) {
+    supervised_user_prefs_ = supervised_user_prefs;
+  }
+  void set_extension_prefs(const scoped_refptr<PrefStore>& extension_prefs) {
+    extension_prefs_ = extension_prefs;
+  }
+  void set_command_line_prefs(
+      const scoped_refptr<PrefStore>& command_line_prefs) {
+    command_line_prefs_ = command_line_prefs;
+  }
+  void set_user_prefs(const scoped_refptr<PersistentPrefStore>& user_prefs) {
+    user_prefs_ = user_prefs;
+  }
+  void set_recommended_prefs(
+      const scoped_refptr<PrefStore>& recommended_prefs) {
+    recommended_prefs_ = recommended_prefs;
+  }
+
+  // Sets up error callback for the PrefService.  A do-nothing default
+  // is provided if this is not called.
+  void set_read_error_callback(
+      const base::Callback<void(PersistentPrefStore::PrefReadError)>&
+          read_error_callback) {
+    read_error_callback_ = read_error_callback;
+  }
+
+  // Specifies to use an actual file-backed user pref store.
+  void SetUserPrefsFile(const base::FilePath& prefs_file,
+                        base::SequencedTaskRunner* task_runner);
+
+  void set_async(bool async) {
+    async_ = async;
+  }
+
+  // Creates a PrefService object initialized with the parameters from
+  // this factory.
+  scoped_ptr<PrefService> Create(PrefRegistry* registry);
+
+ protected:
+  scoped_refptr<PrefStore> managed_prefs_;
+  scoped_refptr<PrefStore> supervised_user_prefs_;
+  scoped_refptr<PrefStore> extension_prefs_;
+  scoped_refptr<PrefStore> command_line_prefs_;
+  scoped_refptr<PersistentPrefStore> user_prefs_;
+  scoped_refptr<PrefStore> recommended_prefs_;
+
+  base::Callback<void(PersistentPrefStore::PrefReadError)> read_error_callback_;
+
+  // Defaults to false.
+  bool async_;
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(PrefServiceFactory);
+};
+
+}  // namespace base
+
+#endif  // BASE_PREFS_PREF_SERVICE_FACTORY_H_
diff --git a/base/prefs/pref_service_unittest.cc b/components/prefs/pref_service_unittest.cc
similarity index 100%
rename from base/prefs/pref_service_unittest.cc
rename to components/prefs/pref_service_unittest.cc
diff --git a/base/prefs/pref_store.cc b/components/prefs/pref_store.cc
similarity index 100%
rename from base/prefs/pref_store.cc
rename to components/prefs/pref_store.cc
diff --git a/components/prefs/pref_store.h b/components/prefs/pref_store.h
new file mode 100644
index 0000000..f95c8c42
--- /dev/null
+++ b/components/prefs/pref_store.h
@@ -0,0 +1,63 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PREF_STORE_H_
+#define BASE_PREFS_PREF_STORE_H_
+
+#include <string>
+
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/prefs/base_prefs_export.h"
+
+namespace base {
+class Value;
+}
+
+// This is an abstract interface for reading and writing from/to a persistent
+// preference store, used by PrefService. An implementation using a JSON file
+// can be found in JsonPrefStore, while an implementation without any backing
+// store for testing can be found in TestingPrefStore. Furthermore, there is
+// CommandLinePrefStore, which bridges command line options to preferences and
+// ConfigurationPolicyPrefStore, which is used for hooking up configuration
+// policy with the preference subsystem.
+class BASE_PREFS_EXPORT PrefStore : public base::RefCounted<PrefStore> {
+ public:
+  // Observer interface for monitoring PrefStore.
+  class BASE_PREFS_EXPORT Observer {
+   public:
+    // Called when the value for the given |key| in the store changes.
+    virtual void OnPrefValueChanged(const std::string& key) = 0;
+    // Notification about the PrefStore being fully initialized.
+    virtual void OnInitializationCompleted(bool succeeded) = 0;
+
+   protected:
+    virtual ~Observer() {}
+  };
+
+  PrefStore() {}
+
+  // Add and remove observers.
+  virtual void AddObserver(Observer* observer) {}
+  virtual void RemoveObserver(Observer* observer) {}
+  virtual bool HasObservers() const;
+
+  // Whether the store has completed all asynchronous initialization.
+  virtual bool IsInitializationComplete() const;
+
+  // Get the value for a given preference |key| and stores it in |*result|.
+  // |*result| is only modified if the return value is true and if |result|
+  // is not NULL. Ownership of the |*result| value remains with the PrefStore.
+  virtual bool GetValue(const std::string& key,
+                        const base::Value** result) const = 0;
+
+ protected:
+  friend class base::RefCounted<PrefStore>;
+  virtual ~PrefStore() {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(PrefStore);
+};
+
+#endif  // BASE_PREFS_PREF_STORE_H_
diff --git a/base/prefs/pref_store_observer_mock.cc b/components/prefs/pref_store_observer_mock.cc
similarity index 100%
rename from base/prefs/pref_store_observer_mock.cc
rename to components/prefs/pref_store_observer_mock.cc
diff --git a/components/prefs/pref_store_observer_mock.h b/components/prefs/pref_store_observer_mock.h
new file mode 100644
index 0000000..1b24b4e0
--- /dev/null
+++ b/components/prefs/pref_store_observer_mock.h
@@ -0,0 +1,35 @@
+// Copyright (c) 2011 The Chromium 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 BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
+#define BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
+
+#include <string>
+#include <vector>
+
+#include "base/compiler_specific.h"
+#include "base/macros.h"
+#include "base/prefs/pref_store.h"
+
+// A mock implementation of PrefStore::Observer.
+class PrefStoreObserverMock : public PrefStore::Observer {
+ public:
+  PrefStoreObserverMock();
+  ~PrefStoreObserverMock() override;
+
+  void VerifyAndResetChangedKey(const std::string& expected);
+
+  // PrefStore::Observer implementation
+  void OnPrefValueChanged(const std::string& key) override;
+  void OnInitializationCompleted(bool success) override;
+
+  std::vector<std::string> changed_keys;
+  bool initialized;
+  bool initialization_success;  // Only valid if |initialized|.
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(PrefStoreObserverMock);
+};
+
+#endif  // BASE_PREFS_PREF_STORE_OBSERVER_MOCK_H_
diff --git a/base/prefs/pref_value_map.cc b/components/prefs/pref_value_map.cc
similarity index 100%
rename from base/prefs/pref_value_map.cc
rename to components/prefs/pref_value_map.cc
diff --git a/components/prefs/pref_value_map.h b/components/prefs/pref_value_map.h
new file mode 100644
index 0000000..349fe68
--- /dev/null
+++ b/components/prefs/pref_value_map.h
@@ -0,0 +1,91 @@
+// Copyright (c) 2011 The Chromium 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 BASE_PREFS_PREF_VALUE_MAP_H_
+#define BASE_PREFS_PREF_VALUE_MAP_H_
+
+#include <string>
+#include <vector>
+
+#include "base/containers/scoped_ptr_hash_map.h"
+#include "base/macros.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/prefs/base_prefs_export.h"
+
+namespace base {
+class Value;
+}
+
+// A generic string to value map used by the PrefStore implementations.
+class BASE_PREFS_EXPORT PrefValueMap {
+ public:
+  using Map = base::ScopedPtrHashMap<std::string, scoped_ptr<base::Value>>;
+  using iterator = Map::iterator;
+  using const_iterator = Map::const_iterator;
+
+  PrefValueMap();
+  virtual ~PrefValueMap();
+
+  // Gets the value for |key| and stores it in |value|. Ownership remains with
+  // the map. Returns true if a value is present. If not, |value| is not
+  // touched.
+  bool GetValue(const std::string& key, const base::Value** value) const;
+  bool GetValue(const std::string& key, base::Value** value);
+
+  // Sets a new |value| for |key|. |value| must be non-null. Returns true if the
+  // value changed.
+  bool SetValue(const std::string& key, scoped_ptr<base::Value> value);
+
+  // Removes the value for |key| from the map. Returns true if a value was
+  // removed.
+  bool RemoveValue(const std::string& key);
+
+  // Clears the map.
+  void Clear();
+
+  // Swaps the contents of two maps.
+  void Swap(PrefValueMap* other);
+
+  iterator begin();
+  iterator end();
+  const_iterator begin() const;
+  const_iterator end() const;
+
+  // Gets a boolean value for |key| and stores it in |value|. Returns true if
+  // the value was found and of the proper type.
+  bool GetBoolean(const std::string& key, bool* value) const;
+
+  // Sets the value for |key| to the boolean |value|.
+  void SetBoolean(const std::string& key, bool value);
+
+  // Gets a string value for |key| and stores it in |value|. Returns true if
+  // the value was found and of the proper type.
+  bool GetString(const std::string& key, std::string* value) const;
+
+  // Sets the value for |key| to the string |value|.
+  void SetString(const std::string& key, const std::string& value);
+
+  // Gets an int value for |key| and stores it in |value|. Returns true if
+  // the value was found and of the proper type.
+  bool GetInteger(const std::string& key, int* value) const;
+
+  // Sets the value for |key| to the int |value|.
+  void SetInteger(const std::string& key, const int value);
+
+  // Sets the value for |key| to the double |value|.
+  void SetDouble(const std::string& key, const double value);
+
+  // Compares this value map against |other| and stores all key names that have
+  // different values in |differing_keys|. This includes keys that are present
+  // only in one of the maps.
+  void GetDifferingKeys(const PrefValueMap* other,
+                        std::vector<std::string>* differing_keys) const;
+
+ private:
+  Map prefs_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefValueMap);
+};
+
+#endif  // BASE_PREFS_PREF_VALUE_MAP_H_
diff --git a/base/prefs/pref_value_map_unittest.cc b/components/prefs/pref_value_map_unittest.cc
similarity index 100%
rename from base/prefs/pref_value_map_unittest.cc
rename to components/prefs/pref_value_map_unittest.cc
diff --git a/base/prefs/pref_value_store.cc b/components/prefs/pref_value_store.cc
similarity index 100%
rename from base/prefs/pref_value_store.cc
rename to components/prefs/pref_value_store.cc
diff --git a/components/prefs/pref_value_store.h b/components/prefs/pref_value_store.h
new file mode 100644
index 0000000..8ec8c59
--- /dev/null
+++ b/components/prefs/pref_value_store.h
@@ -0,0 +1,260 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_PREF_VALUE_STORE_H_
+#define BASE_PREFS_PREF_VALUE_STORE_H_
+
+#include <map>
+#include <string>
+#include <vector>
+
+#include "base/callback.h"
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_store.h"
+#include "base/values.h"
+
+class PrefNotifier;
+class PrefStore;
+
+// The PrefValueStore manages various sources of values for Preferences
+// (e.g., configuration policies, extensions, and user settings). It returns
+// the value of a Preference from the source with the highest priority, and
+// allows setting user-defined values for preferences that are not managed.
+//
+// Unless otherwise explicitly noted, all of the methods of this class must
+// be called on the UI thread.
+class BASE_PREFS_EXPORT PrefValueStore {
+ public:
+  typedef base::Callback<void(const std::string&)> PrefChangedCallback;
+
+  // In decreasing order of precedence:
+  //   |managed_prefs| contains all preferences from mandatory policies.
+  //   |supervised_user_prefs| contains all preferences from supervised user
+  //        settings, i.e. settings configured for a supervised user by their
+  //        custodian.
+  //   |extension_prefs| contains preference values set by extensions.
+  //   |command_line_prefs| contains preference values set by command-line
+  //        switches.
+  //   |user_prefs| contains all user-set preference values.
+  //   |recommended_prefs| contains all preferences from recommended policies.
+  //   |default_prefs| contains application-default preference values. It must
+  //        be non-null if any preferences are to be registered.
+  //
+  // |pref_notifier| facilitates broadcasting preference change notifications
+  // to the world.
+  PrefValueStore(PrefStore* managed_prefs,
+                 PrefStore* supervised_user_prefs,
+                 PrefStore* extension_prefs,
+                 PrefStore* command_line_prefs,
+                 PrefStore* user_prefs,
+                 PrefStore* recommended_prefs,
+                 PrefStore* default_prefs,
+                 PrefNotifier* pref_notifier);
+  virtual ~PrefValueStore();
+
+  // Creates a clone of this PrefValueStore with PrefStores overwritten
+  // by the parameters passed, if unequal NULL.
+  PrefValueStore* CloneAndSpecialize(PrefStore* managed_prefs,
+                                     PrefStore* supervised_user_prefs,
+                                     PrefStore* extension_prefs,
+                                     PrefStore* command_line_prefs,
+                                     PrefStore* user_prefs,
+                                     PrefStore* recommended_prefs,
+                                     PrefStore* default_prefs,
+                                     PrefNotifier* pref_notifier);
+
+  // A PrefValueStore can have exactly one callback that is directly
+  // notified of preferences changing in the store. This does not
+  // filter through the PrefNotifier mechanism, which may not forward
+  // certain changes (e.g. unregistered prefs).
+  void set_callback(const PrefChangedCallback& callback);
+
+  // Gets the value for the given preference name that has the specified value
+  // type. Values stored in a PrefStore that have the matching |name| but
+  // a non-matching |type| are silently skipped. Returns true if a valid value
+  // was found in any of the available PrefStores. Most callers should use
+  // Preference::GetValue() instead of calling this method directly.
+  bool GetValue(const std::string& name,
+                base::Value::Type type,
+                const base::Value** out_value) const;
+
+  // Gets the recommended value for the given preference name that has the
+  // specified value type. A value stored in the recommended PrefStore that has
+  // the matching |name| but a non-matching |type| is silently ignored. Returns
+  // true if a valid value was found. Most callers should use
+  // Preference::GetRecommendedValue() instead of calling this method directly.
+  bool GetRecommendedValue(const std::string& name,
+                           base::Value::Type type,
+                           const base::Value** out_value) const;
+
+  // These methods return true if a preference with the given name is in the
+  // indicated pref store, even if that value is currently being overridden by
+  // a higher-priority source.
+  bool PrefValueInManagedStore(const std::string& name) const;
+  bool PrefValueInSupervisedStore(const std::string& name) const;
+  bool PrefValueInExtensionStore(const std::string& name) const;
+  bool PrefValueInUserStore(const std::string& name) const;
+
+  // These methods return true if a preference with the given name is actually
+  // being controlled by the indicated pref store and not being overridden by
+  // a higher-priority source.
+  bool PrefValueFromExtensionStore(const std::string& name) const;
+  bool PrefValueFromUserStore(const std::string& name) const;
+  bool PrefValueFromRecommendedStore(const std::string& name) const;
+  bool PrefValueFromDefaultStore(const std::string& name) const;
+
+  // Check whether a Preference value is modifiable by the user, i.e. whether
+  // there is no higher-priority source controlling it.
+  bool PrefValueUserModifiable(const std::string& name) const;
+
+  // Check whether a Preference value is modifiable by an extension, i.e.
+  // whether there is no higher-priority source controlling it.
+  bool PrefValueExtensionModifiable(const std::string& name) const;
+
+  // Update the command line PrefStore with |command_line_prefs|.
+  void UpdateCommandLinePrefStore(PrefStore* command_line_prefs);
+
+ private:
+  // PrefStores must be listed here in order from highest to lowest priority.
+  //   MANAGED contains all managed preference values that are provided by
+  //      mandatory policies (e.g. Windows Group Policy or cloud policy).
+  //   SUPERVISED_USER contains preferences that are valid for supervised users.
+  //   EXTENSION contains preference values set by extensions.
+  //   COMMAND_LINE contains preference values set by command-line switches.
+  //   USER contains all user-set preference values.
+  //   RECOMMENDED contains all preferences that are provided by recommended
+  //      policies.
+  //   DEFAULT contains all application default preference values.
+  enum PrefStoreType {
+    // INVALID_STORE is not associated with an actual PrefStore but used as
+    // an invalid marker, e.g. as a return value.
+    INVALID_STORE = -1,
+    MANAGED_STORE = 0,
+    SUPERVISED_USER_STORE,
+    EXTENSION_STORE,
+    COMMAND_LINE_STORE,
+    USER_STORE,
+    RECOMMENDED_STORE,
+    DEFAULT_STORE,
+    PREF_STORE_TYPE_MAX = DEFAULT_STORE
+  };
+
+  // Keeps a PrefStore reference on behalf of the PrefValueStore and monitors
+  // the PrefStore for changes, forwarding notifications to PrefValueStore. This
+  // indirection is here for the sake of disambiguating notifications from the
+  // individual PrefStores.
+  class PrefStoreKeeper : public PrefStore::Observer {
+   public:
+    PrefStoreKeeper();
+    ~PrefStoreKeeper() override;
+
+    // Takes ownership of |pref_store|.
+    void Initialize(PrefValueStore* store,
+                    PrefStore* pref_store,
+                    PrefStoreType type);
+
+    PrefStore* store() { return pref_store_.get(); }
+    const PrefStore* store() const { return pref_store_.get(); }
+
+   private:
+    // PrefStore::Observer implementation.
+    void OnPrefValueChanged(const std::string& key) override;
+    void OnInitializationCompleted(bool succeeded) override;
+
+    // PrefValueStore this keeper is part of.
+    PrefValueStore* pref_value_store_;
+
+    // The PrefStore managed by this keeper.
+    scoped_refptr<PrefStore> pref_store_;
+
+    // Type of the pref store.
+    PrefStoreType type_;
+
+    DISALLOW_COPY_AND_ASSIGN(PrefStoreKeeper);
+  };
+
+  typedef std::map<std::string, base::Value::Type> PrefTypeMap;
+
+  // Returns true if the preference with the given name has a value in the
+  // given PrefStoreType, of the same value type as the preference was
+  // registered with.
+  bool PrefValueInStore(const std::string& name, PrefStoreType store) const;
+
+  // Returns true if a preference has an explicit value in any of the
+  // stores in the range specified by |first_checked_store| and
+  // |last_checked_store|, even if that value is currently being
+  // overridden by a higher-priority store.
+  bool PrefValueInStoreRange(const std::string& name,
+                             PrefStoreType first_checked_store,
+                             PrefStoreType last_checked_store) const;
+
+  // Returns the pref store type identifying the source that controls the
+  // Preference identified by |name|. If none of the sources has a value,
+  // INVALID_STORE is returned. In practice, the default PrefStore
+  // should always have a value for any registered preferencem, so INVALID_STORE
+  // indicates an error.
+  PrefStoreType ControllingPrefStoreForPref(const std::string& name) const;
+
+  // Get a value from the specified |store|.
+  bool GetValueFromStore(const std::string& name,
+                         PrefStoreType store,
+                         const base::Value** out_value) const;
+
+  // Get a value from the specified |store| if its |type| matches.
+  bool GetValueFromStoreWithType(const std::string& name,
+                                 base::Value::Type type,
+                                 PrefStoreType store,
+                                 const base::Value** out_value) const;
+
+  // Called upon changes in individual pref stores in order to determine whether
+  // the user-visible pref value has changed. Triggers the change notification
+  // if the effective value of the preference has changed, or if the store
+  // controlling the pref has changed.
+  void NotifyPrefChanged(const std::string& path, PrefStoreType new_store);
+
+  // Called from the PrefStoreKeeper implementation when a pref value for |key|
+  // changed in the pref store for |type|.
+  void OnPrefValueChanged(PrefStoreType type, const std::string& key);
+
+  // Handle the event that the store for |type| has completed initialization.
+  void OnInitializationCompleted(PrefStoreType type, bool succeeded);
+
+  // Initializes a pref store keeper. Sets up a PrefStoreKeeper that will take
+  // ownership of the passed |pref_store|.
+  void InitPrefStore(PrefStoreType type, PrefStore* pref_store);
+
+  // Checks whether initialization is completed and tells the notifier if that
+  // is the case.
+  void CheckInitializationCompleted();
+
+  // Get the PrefStore pointer for the given type. May return NULL if there is
+  // no PrefStore for that type.
+  PrefStore* GetPrefStore(PrefStoreType type) {
+    return pref_stores_[type].store();
+  }
+  const PrefStore* GetPrefStore(PrefStoreType type) const {
+    return pref_stores_[type].store();
+  }
+
+  // Keeps the PrefStore references in order of precedence.
+  PrefStoreKeeper pref_stores_[PREF_STORE_TYPE_MAX + 1];
+
+  PrefChangedCallback pref_changed_callback_;
+
+  // Used for generating notifications. This is a weak reference,
+  // since the notifier is owned by the corresponding PrefService.
+  PrefNotifier* pref_notifier_;
+
+  // A mapping of preference names to their registered types.
+  PrefTypeMap pref_types_;
+
+  // True if not all of the PrefStores were initialized successfully.
+  bool initialization_failed_;
+
+  DISALLOW_COPY_AND_ASSIGN(PrefValueStore);
+};
+
+#endif  // BASE_PREFS_PREF_VALUE_STORE_H_
diff --git a/base/prefs/pref_value_store_unittest.cc b/components/prefs/pref_value_store_unittest.cc
similarity index 100%
rename from base/prefs/pref_value_store_unittest.cc
rename to components/prefs/pref_value_store_unittest.cc
diff --git a/components/prefs/prefs.gyp b/components/prefs/prefs.gyp
new file mode 100644
index 0000000..ed9c58a
--- /dev/null
+++ b/components/prefs/prefs.gyp
@@ -0,0 +1,87 @@
+# Copyright (c) 2013 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+{
+  'targets': [
+    {
+      'target_name': 'prefs',
+      'type': '<(component)',
+      'dependencies': [
+        '../../base/base.gyp:base',
+      ],
+      'include_dirs': [
+        '../..',
+      ],
+      'defines': [
+        'BASE_PREFS_IMPLEMENTATION',
+      ],
+      'sources': [
+        'default_pref_store.cc',
+        'default_pref_store.h',
+        'json_pref_store.cc',
+        'json_pref_store.h',
+        'overlay_user_pref_store.cc',
+        'overlay_user_pref_store.h',
+        'pref_change_registrar.cc',
+        'pref_change_registrar.h',
+        'pref_member.cc',
+        'pref_member.h',
+        'pref_notifier_impl.cc',
+        'pref_notifier_impl.h',
+        'pref_registry.cc',
+        'pref_registry.h',
+        'pref_registry_simple.cc',
+        'pref_registry_simple.h',
+        'pref_service.cc',
+        'pref_service.h',
+        'pref_service_factory.cc',
+        'pref_service_factory.h',
+        'pref_store.cc',
+        'pref_store.h',
+        'pref_value_map.cc',
+        'pref_value_map.h',
+        'pref_value_store.cc',
+        'pref_value_store.h',
+        'scoped_user_pref_update.cc',
+        'scoped_user_pref_update.h',
+        'value_map_pref_store.cc',
+        'value_map_pref_store.h',
+      ],
+      'conditions': [
+        ['OS!="ios"', {
+          'sources': [
+            'base_prefs_export.h',
+            'persistent_pref_store.h',
+            'pref_filter.h',
+            'pref_notifier.h',
+            'pref_observer.h',
+            'writeable_pref_store.h',
+          ]
+        }]
+      ],
+    },
+    {
+      'target_name': 'prefs_test_support',
+      'type': 'static_library',
+      'include_dirs': [
+        '../..',
+      ],
+      'dependencies': [
+        'prefs',
+        '<(DEPTH)/testing/gmock.gyp:gmock',
+        '<(DEPTH)/testing/gtest.gyp:gtest',
+      ],
+      'sources': [
+        'mock_pref_change_callback.cc',
+        'mock_pref_change_callback.h',
+        'pref_store_observer_mock.cc',
+        'pref_store_observer_mock.h',
+        'testing_pref_service.cc',
+        'testing_pref_service.h',
+        'testing_pref_store.cc',
+        'testing_pref_store.h',
+      ],
+    },
+  ],
+}
diff --git a/base/prefs/scoped_user_pref_update.cc b/components/prefs/scoped_user_pref_update.cc
similarity index 100%
rename from base/prefs/scoped_user_pref_update.cc
rename to components/prefs/scoped_user_pref_update.cc
diff --git a/components/prefs/scoped_user_pref_update.h b/components/prefs/scoped_user_pref_update.h
new file mode 100644
index 0000000..29ad852
--- /dev/null
+++ b/components/prefs/scoped_user_pref_update.h
@@ -0,0 +1,108 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+//
+// A helper class that assists preferences in firing notifications when lists
+// or dictionaries are changed.
+
+#ifndef BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
+#define BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
+
+#include <string>
+
+#include "base/macros.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_service.h"
+#include "base/threading/non_thread_safe.h"
+#include "base/values.h"
+
+class PrefService;
+
+namespace base {
+class DictionaryValue;
+class ListValue;
+}
+
+namespace subtle {
+
+// Base class for ScopedUserPrefUpdateTemplate that contains the parts
+// that do not depend on ScopedUserPrefUpdateTemplate's template parameter.
+//
+// We need this base class mostly for making it a friend of PrefService
+// and getting access to PrefService::GetMutableUserPref and
+// PrefService::ReportUserPrefChanged.
+class BASE_PREFS_EXPORT ScopedUserPrefUpdateBase : public base::NonThreadSafe {
+ protected:
+  ScopedUserPrefUpdateBase(PrefService* service, const std::string& path);
+
+  // Calls Notify().
+  ~ScopedUserPrefUpdateBase();
+
+  // Sets |value_| to |service_|->GetMutableUserPref and returns it.
+  base::Value* GetValueOfType(base::Value::Type type);
+
+ private:
+  // If |value_| is not null, triggers a notification of PrefObservers and
+  // resets |value_|.
+  void Notify();
+
+  // Weak pointer.
+  PrefService* service_;
+  // Path of the preference being updated.
+  std::string path_;
+  // Cache of value from user pref store (set between Get() and Notify() calls).
+  base::Value* value_;
+
+  DISALLOW_COPY_AND_ASSIGN(ScopedUserPrefUpdateBase);
+};
+
+}  // namespace subtle
+
+// Class to support modifications to DictionaryValues and ListValues while
+// guaranteeing that PrefObservers are notified of changed values.
+//
+// This class may only be used on the UI thread as it requires access to the
+// PrefService.
+template <typename T, base::Value::Type type_enum_value>
+class ScopedUserPrefUpdate : public subtle::ScopedUserPrefUpdateBase {
+ public:
+  ScopedUserPrefUpdate(PrefService* service, const std::string& path)
+      : ScopedUserPrefUpdateBase(service, path) {}
+
+  // Triggers an update notification if Get() was called.
+  virtual ~ScopedUserPrefUpdate() {}
+
+  // Returns a mutable |T| instance that
+  // - is already in the user pref store, or
+  // - is (silently) created and written to the user pref store if none existed
+  //   before.
+  //
+  // Calling Get() implies that an update notification is necessary at
+  // destruction time.
+  //
+  // The ownership of the return value remains with the user pref store.
+  // Virtual so it can be overriden in subclasses that transform the value
+  // before returning it (for example to return a subelement of a dictionary).
+  virtual T* Get() {
+    return static_cast<T*>(GetValueOfType(type_enum_value));
+  }
+
+  T& operator*() {
+    return *Get();
+  }
+
+  T* operator->() {
+    return Get();
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(ScopedUserPrefUpdate);
+};
+
+typedef ScopedUserPrefUpdate<base::DictionaryValue,
+                             base::Value::TYPE_DICTIONARY>
+    DictionaryPrefUpdate;
+typedef ScopedUserPrefUpdate<base::ListValue, base::Value::TYPE_LIST>
+    ListPrefUpdate;
+
+#endif  // BASE_PREFS_SCOPED_USER_PREF_UPDATE_H_
diff --git a/base/prefs/scoped_user_pref_update_unittest.cc b/components/prefs/scoped_user_pref_update_unittest.cc
similarity index 100%
rename from base/prefs/scoped_user_pref_update_unittest.cc
rename to components/prefs/scoped_user_pref_update_unittest.cc
diff --git a/base/prefs/testing_pref_service.cc b/components/prefs/testing_pref_service.cc
similarity index 100%
rename from base/prefs/testing_pref_service.cc
rename to components/prefs/testing_pref_service.cc
diff --git a/components/prefs/testing_pref_service.h b/components/prefs/testing_pref_service.h
new file mode 100644
index 0000000..85a2879
--- /dev/null
+++ b/components/prefs/testing_pref_service.h
@@ -0,0 +1,196 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_TESTING_PREF_SERVICE_H_
+#define BASE_PREFS_TESTING_PREF_SERVICE_H_
+
+#include "base/macros.h"
+#include "base/memory/ref_counted.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/prefs/pref_registry.h"
+#include "base/prefs/pref_service.h"
+#include "base/prefs/testing_pref_store.h"
+
+class PrefNotifierImpl;
+class PrefRegistrySimple;
+class TestingPrefStore;
+
+// A PrefService subclass for testing. It operates totally in memory and
+// provides additional API for manipulating preferences at the different levels
+// (managed, extension, user) conveniently.
+//
+// Use this via its specializations, e.g. TestingPrefServiceSimple.
+template <class SuperPrefService, class ConstructionPrefRegistry>
+class TestingPrefServiceBase : public SuperPrefService {
+ public:
+  virtual ~TestingPrefServiceBase();
+
+  // Read the value of a preference from the managed layer. Returns NULL if the
+  // preference is not defined at the managed layer.
+  const base::Value* GetManagedPref(const std::string& path) const;
+
+  // Set a preference on the managed layer and fire observers if the preference
+  // changed. Assumes ownership of |value|.
+  void SetManagedPref(const std::string& path, base::Value* value);
+
+  // Clear the preference on the managed layer and fire observers if the
+  // preference has been defined previously.
+  void RemoveManagedPref(const std::string& path);
+
+  // Similar to the above, but for user preferences.
+  const base::Value* GetUserPref(const std::string& path) const;
+  void SetUserPref(const std::string& path, base::Value* value);
+  void RemoveUserPref(const std::string& path);
+
+  // Similar to the above, but for recommended policy preferences.
+  const base::Value* GetRecommendedPref(const std::string& path) const;
+  void SetRecommendedPref(const std::string& path, base::Value* value);
+  void RemoveRecommendedPref(const std::string& path);
+
+  // Do-nothing implementation for TestingPrefService.
+  static void HandleReadError(PersistentPrefStore::PrefReadError error) {}
+
+ protected:
+  TestingPrefServiceBase(
+      TestingPrefStore* managed_prefs,
+      TestingPrefStore* user_prefs,
+      TestingPrefStore* recommended_prefs,
+      ConstructionPrefRegistry* pref_registry,
+      PrefNotifierImpl* pref_notifier);
+
+ private:
+  // Reads the value of the preference indicated by |path| from |pref_store|.
+  // Returns NULL if the preference was not found.
+  const base::Value* GetPref(TestingPrefStore* pref_store,
+                             const std::string& path) const;
+
+  // Sets the value for |path| in |pref_store|.
+  void SetPref(TestingPrefStore* pref_store,
+               const std::string& path,
+               base::Value* value);
+
+  // Removes the preference identified by |path| from |pref_store|.
+  void RemovePref(TestingPrefStore* pref_store, const std::string& path);
+
+  // Pointers to the pref stores our value store uses.
+  scoped_refptr<TestingPrefStore> managed_prefs_;
+  scoped_refptr<TestingPrefStore> user_prefs_;
+  scoped_refptr<TestingPrefStore> recommended_prefs_;
+
+  DISALLOW_COPY_AND_ASSIGN(TestingPrefServiceBase);
+};
+
+// Test version of PrefService.
+class TestingPrefServiceSimple
+    : public TestingPrefServiceBase<PrefService, PrefRegistry> {
+ public:
+  TestingPrefServiceSimple();
+  ~TestingPrefServiceSimple() override;
+
+  // This is provided as a convenience for registering preferences on
+  // an existing TestingPrefServiceSimple instance. On a production
+  // PrefService you would do all registrations before constructing
+  // it, passing it a PrefRegistry via its constructor (or via
+  // e.g. PrefServiceFactory).
+  PrefRegistrySimple* registry();
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(TestingPrefServiceSimple);
+};
+
+template<>
+TestingPrefServiceBase<PrefService, PrefRegistry>::TestingPrefServiceBase(
+    TestingPrefStore* managed_prefs,
+    TestingPrefStore* user_prefs,
+    TestingPrefStore* recommended_prefs,
+    PrefRegistry* pref_registry,
+    PrefNotifierImpl* pref_notifier);
+
+template<class SuperPrefService, class ConstructionPrefRegistry>
+TestingPrefServiceBase<
+    SuperPrefService, ConstructionPrefRegistry>::~TestingPrefServiceBase() {
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+const base::Value* TestingPrefServiceBase<
+    SuperPrefService,
+    ConstructionPrefRegistry>::GetManagedPref(const std::string& path) const {
+  return GetPref(managed_prefs_.get(), path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    SetManagedPref(const std::string& path, base::Value* value) {
+  SetPref(managed_prefs_.get(), path, value);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    RemoveManagedPref(const std::string& path) {
+  RemovePref(managed_prefs_.get(), path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+const base::Value*
+TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::GetUserPref(
+    const std::string& path) const {
+  return GetPref(user_prefs_.get(), path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    SetUserPref(const std::string& path, base::Value* value) {
+  SetPref(user_prefs_.get(), path, value);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    RemoveUserPref(const std::string& path) {
+  RemovePref(user_prefs_.get(), path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+const base::Value*
+TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    GetRecommendedPref(const std::string& path) const {
+  return GetPref(recommended_prefs_, path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    SetRecommendedPref(const std::string& path, base::Value* value) {
+  SetPref(recommended_prefs_.get(), path, value);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    RemoveRecommendedPref(const std::string& path) {
+  RemovePref(recommended_prefs_.get(), path);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+const base::Value*
+TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::GetPref(
+    TestingPrefStore* pref_store,
+    const std::string& path) const {
+  const base::Value* res;
+  return pref_store->GetValue(path, &res) ? res : NULL;
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    SetPref(TestingPrefStore* pref_store,
+            const std::string& path,
+            base::Value* value) {
+  pref_store->SetValue(path, make_scoped_ptr(value),
+                       WriteablePrefStore::DEFAULT_PREF_WRITE_FLAGS);
+}
+
+template <class SuperPrefService, class ConstructionPrefRegistry>
+void TestingPrefServiceBase<SuperPrefService, ConstructionPrefRegistry>::
+    RemovePref(TestingPrefStore* pref_store, const std::string& path) {
+  pref_store->RemoveValue(path, WriteablePrefStore::DEFAULT_PREF_WRITE_FLAGS);
+}
+
+#endif  // BASE_PREFS_TESTING_PREF_SERVICE_H_
diff --git a/base/prefs/testing_pref_store.cc b/components/prefs/testing_pref_store.cc
similarity index 100%
rename from base/prefs/testing_pref_store.cc
rename to components/prefs/testing_pref_store.cc
diff --git a/components/prefs/testing_pref_store.h b/components/prefs/testing_pref_store.h
new file mode 100644
index 0000000..713e69a7
--- /dev/null
+++ b/components/prefs/testing_pref_store.h
@@ -0,0 +1,114 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_TESTING_PREF_STORE_H_
+#define BASE_PREFS_TESTING_PREF_STORE_H_
+
+#include <stdint.h>
+
+#include <string>
+
+#include "base/compiler_specific.h"
+#include "base/macros.h"
+#include "base/observer_list.h"
+#include "base/prefs/persistent_pref_store.h"
+#include "base/prefs/pref_value_map.h"
+
+// |TestingPrefStore| is a preference store implementation that allows tests to
+// explicitly manipulate the contents of the store, triggering notifications
+// where appropriate.
+class TestingPrefStore : public PersistentPrefStore {
+ public:
+  TestingPrefStore();
+
+  // Overriden from PrefStore.
+  bool GetValue(const std::string& key,
+                const base::Value** result) const override;
+  void AddObserver(PrefStore::Observer* observer) override;
+  void RemoveObserver(PrefStore::Observer* observer) override;
+  bool HasObservers() const override;
+  bool IsInitializationComplete() const override;
+
+  // PersistentPrefStore overrides:
+  bool GetMutableValue(const std::string& key, base::Value** result) override;
+  void ReportValueChanged(const std::string& key, uint32_t flags) override;
+  void SetValue(const std::string& key,
+                scoped_ptr<base::Value> value,
+                uint32_t flags) override;
+  void SetValueSilently(const std::string& key,
+                        scoped_ptr<base::Value> value,
+                        uint32_t flags) override;
+  void RemoveValue(const std::string& key, uint32_t flags) override;
+  bool ReadOnly() const override;
+  PrefReadError GetReadError() const override;
+  PersistentPrefStore::PrefReadError ReadPrefs() override;
+  void ReadPrefsAsync(ReadErrorDelegate* error_delegate) override;
+  void CommitPendingWrite() override;
+  void SchedulePendingLossyWrites() override;
+
+  // Marks the store as having completed initialization.
+  void SetInitializationCompleted();
+
+  // Used for tests to trigger notifications explicitly.
+  void NotifyPrefValueChanged(const std::string& key);
+  void NotifyInitializationCompleted();
+
+  // Some convenience getters/setters.
+  void SetString(const std::string& key, const std::string& value);
+  void SetInteger(const std::string& key, int value);
+  void SetBoolean(const std::string& key, bool value);
+
+  bool GetString(const std::string& key, std::string* value) const;
+  bool GetInteger(const std::string& key, int* value) const;
+  bool GetBoolean(const std::string& key, bool* value) const;
+
+  // Determines whether ReadPrefsAsync completes immediately. Defaults to false
+  // (non-blocking). To block, invoke this with true (blocking) before the call
+  // to ReadPrefsAsync. To unblock, invoke again with false (non-blocking) after
+  // the call to ReadPrefsAsync.
+  void SetBlockAsyncRead(bool block_async_read);
+
+  // Getter and Setter methods for setting and getting the state of the
+  // |TestingPrefStore|.
+  virtual void set_read_only(bool read_only);
+  void set_read_success(bool read_success);
+  void set_read_error(PersistentPrefStore::PrefReadError read_error);
+  bool committed() { return committed_; }
+
+ protected:
+  ~TestingPrefStore() override;
+
+ private:
+  // Stores the preference values.
+  PrefValueMap prefs_;
+
+  // Flag that indicates if the PrefStore is read-only
+  bool read_only_;
+
+  // The result to pass to PrefStore::Observer::OnInitializationCompleted
+  bool read_success_;
+
+  // The result to return from ReadPrefs or ReadPrefsAsync.
+  PersistentPrefStore::PrefReadError read_error_;
+
+  // Whether a call to ReadPrefsAsync should block.
+  bool block_async_read_;
+
+  // Whether there is a pending call to ReadPrefsAsync.
+  bool pending_async_read_;
+
+  // Whether initialization has been completed.
+  bool init_complete_;
+
+  // Whether the store contents have been committed to disk since the last
+  // mutation.
+  bool committed_;
+
+  scoped_ptr<ReadErrorDelegate> error_delegate_;
+  base::ObserverList<PrefStore::Observer, true> observers_;
+
+  DISALLOW_COPY_AND_ASSIGN(TestingPrefStore);
+};
+
+#endif  // BASE_PREFS_TESTING_PREF_STORE_H_
diff --git a/base/prefs/value_map_pref_store.cc b/components/prefs/value_map_pref_store.cc
similarity index 100%
rename from base/prefs/value_map_pref_store.cc
rename to components/prefs/value_map_pref_store.cc
diff --git a/components/prefs/value_map_pref_store.h b/components/prefs/value_map_pref_store.h
new file mode 100644
index 0000000..eac785d
--- /dev/null
+++ b/components/prefs/value_map_pref_store.h
@@ -0,0 +1,57 @@
+// Copyright (c) 2012 The Chromium 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 BASE_PREFS_VALUE_MAP_PREF_STORE_H_
+#define BASE_PREFS_VALUE_MAP_PREF_STORE_H_
+
+#include <stdint.h>
+
+#include <map>
+#include <string>
+
+#include "base/macros.h"
+#include "base/observer_list.h"
+#include "base/prefs/base_prefs_export.h"
+#include "base/prefs/pref_value_map.h"
+#include "base/prefs/writeable_pref_store.h"
+
+// A basic PrefStore implementation that uses a simple name-value map for
+// storing the preference values.
+class BASE_PREFS_EXPORT ValueMapPrefStore : public WriteablePrefStore {
+ public:
+  ValueMapPrefStore();
+
+  // PrefStore overrides:
+  bool GetValue(const std::string& key,
+                const base::Value** value) const override;
+  void AddObserver(PrefStore::Observer* observer) override;
+  void RemoveObserver(PrefStore::Observer* observer) override;
+  bool HasObservers() const override;
+
+  // WriteablePrefStore overrides:
+  void SetValue(const std::string& key,
+                scoped_ptr<base::Value> value,
+                uint32_t flags) override;
+  void RemoveValue(const std::string& key, uint32_t flags) override;
+  bool GetMutableValue(const std::string& key, base::Value** value) override;
+  void ReportValueChanged(const std::string& key, uint32_t flags) override;
+  void SetValueSilently(const std::string& key,
+                        scoped_ptr<base::Value> value,
+                        uint32_t flags) override;
+
+ protected:
+  ~ValueMapPrefStore() override;
+
+  // Notify observers about the initialization completed event.
+  void NotifyInitializationCompleted();
+
+ private:
+  PrefValueMap prefs_;
+
+  base::ObserverList<PrefStore::Observer, true> observers_;
+
+  DISALLOW_COPY_AND_ASSIGN(ValueMapPrefStore);
+};
+
+#endif  // BASE_PREFS_VALUE_MAP_PREF_STORE_H_
diff --git a/components/prefs/writeable_pref_store.h b/components/prefs/writeable_pref_store.h
new file mode 100644
index 0000000..f7da279a
--- /dev/null
+++ b/components/prefs/writeable_pref_store.h
@@ -0,0 +1,72 @@
+// Copyright 2014 The Chromium 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 BASE_PREFS_WRITEABLE_PREF_STORE_H_
+#define BASE_PREFS_WRITEABLE_PREF_STORE_H_
+
+#include <stdint.h>
+
+#include <string>
+
+#include "base/macros.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/prefs/pref_store.h"
+
+namespace base {
+class Value;
+}
+
+// A pref store that can be written to as well as read from.
+class BASE_PREFS_EXPORT WriteablePrefStore : public PrefStore {
+ public:
+  // PrefWriteFlags can be used to change the way a pref will be written to
+  // storage.
+  enum PrefWriteFlags : uint32_t {
+    // No flags are specified.
+    DEFAULT_PREF_WRITE_FLAGS = 0,
+
+    // This marks the pref as "lossy". There is no strict time guarantee on when
+    // a lossy pref will be persisted to permanent storage when it is modified.
+    LOSSY_PREF_WRITE_FLAG = 1 << 1
+  };
+
+  WriteablePrefStore() {}
+
+  // Sets a |value| for |key| in the store. |value| must be non-NULL. |flags| is
+  // a bitmask of PrefWriteFlags.
+  virtual void SetValue(const std::string& key,
+                        scoped_ptr<base::Value> value,
+                        uint32_t flags) = 0;
+
+  // Removes the value for |key|.
+  virtual void RemoveValue(const std::string& key, uint32_t flags) = 0;
+
+  // Equivalent to PrefStore::GetValue but returns a mutable value.
+  virtual bool GetMutableValue(const std::string& key,
+                               base::Value** result) = 0;
+
+  // Triggers a value changed notification. This function needs to be called
+  // if one retrieves a list or dictionary with GetMutableValue and change its
+  // value. SetValue takes care of notifications itself. Note that
+  // ReportValueChanged will trigger notifications even if nothing has changed.
+  // |flags| is a bitmask of PrefWriteFlags.
+  virtual void ReportValueChanged(const std::string& key, uint32_t flags) = 0;
+
+  // Same as SetValue, but doesn't generate notifications. This is used by
+  // PrefService::GetMutableUserPref() in order to put empty entries
+  // into the user pref store. Using SetValue is not an option since existing
+  // tests rely on the number of notifications generated. |flags| is a bitmask
+  // of PrefWriteFlags.
+  virtual void SetValueSilently(const std::string& key,
+                                scoped_ptr<base::Value> value,
+                                uint32_t flags) = 0;
+
+ protected:
+  ~WriteablePrefStore() override {}
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(WriteablePrefStore);
+};
+
+#endif  // BASE_PREFS_WRITEABLE_PREF_STORE_H_
diff --git a/components/proximity_auth.gypi b/components/proximity_auth.gypi
index 60f952ab..13486d4 100644
--- a/components/proximity_auth.gypi
+++ b/components/proximity_auth.gypi
@@ -17,9 +17,9 @@
         ':cryptauth_proto',
         ':proximity_auth_logging',
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../device/bluetooth/bluetooth.gyp:device_bluetooth',
         '../net/net.gyp:net',
+        'prefs/prefs.gyp:prefs',
       ],
       'sources': [
         "proximity_auth/authenticator.h",
diff --git a/components/proximity_auth/BUILD.gn b/components/proximity_auth/BUILD.gn
index 565e1d2..a19418d8 100644
--- a/components/proximity_auth/BUILD.gn
+++ b/components/proximity_auth/BUILD.gn
@@ -71,7 +71,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/proximity_auth/ble",
     "//components/proximity_auth/cryptauth",
     "//components/proximity_auth/logging",
@@ -149,8 +149,8 @@
     ":proximity_auth",
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//components/proximity_auth/ble:unit_tests",
     "//components/proximity_auth/cryptauth:test_support",
     "//components/proximity_auth/cryptauth:unit_tests",
diff --git a/components/proximity_auth/ble/BUILD.gn b/components/proximity_auth/ble/BUILD.gn
index 1be48bd..29ae3ba 100644
--- a/components/proximity_auth/ble/BUILD.gn
+++ b/components/proximity_auth/ble/BUILD.gn
@@ -23,7 +23,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/proximity_auth/logging",
 
     # TODO(https://crbug.com/562683): This component has a circular dependency
@@ -52,8 +52,8 @@
 
   deps = [
     ":ble",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//components/proximity_auth:test_support",
     "//device/bluetooth:mocks",
     "//testing/gmock",
diff --git a/components/proximity_auth/cryptauth/BUILD.gn b/components/proximity_auth/cryptauth/BUILD.gn
index aa3bf55..fc7d40e 100644
--- a/components/proximity_auth/cryptauth/BUILD.gn
+++ b/components/proximity_auth/cryptauth/BUILD.gn
@@ -39,9 +39,9 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/gcm_driver",
     "//components/gcm_driver/common",
+    "//components/prefs",
     "//components/proximity_auth/logging",
     "//crypto",
     "//google_apis",
@@ -95,9 +95,9 @@
   deps = [
     ":cryptauth",
     ":test_support",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/gcm_driver:test_support",
+    "//components/prefs:test_support",
     "//components/proximity_auth",
     "//google_apis:test_support",
     "//net:test_support",
diff --git a/components/proximity_auth/webui/BUILD.gn b/components/proximity_auth/webui/BUILD.gn
index db5e634..e3cb0b6e 100644
--- a/components/proximity_auth/webui/BUILD.gn
+++ b/components/proximity_auth/webui/BUILD.gn
@@ -18,7 +18,7 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
+    "//components/prefs",
     "//components/proximity_auth",
     "//components/proximity_auth/ble",
     "//components/proximity_auth/cryptauth",
diff --git a/components/proxy_config.gypi b/components/proxy_config.gypi
index 985bf11..f30b9f8 100644
--- a/components/proxy_config.gypi
+++ b/components/proxy_config.gypi
@@ -10,10 +10,10 @@
       'type': '<(component)',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../net/net.gyp:net',
         '../url/url.gyp:url_lib',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/proxy_config/BUILD.gn b/components/proxy_config/BUILD.gn
index 6430d948..3243526f 100644
--- a/components/proxy_config/BUILD.gn
+++ b/components/proxy_config/BUILD.gn
@@ -24,7 +24,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//net",
     "//url",
   ]
@@ -50,8 +50,8 @@
   deps = [
     ":proxy_config",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//net",
     "//testing/gmock",
     "//testing/gtest",
diff --git a/components/rappor/BUILD.gn b/components/rappor/BUILD.gn
index badab65..ba09d373 100644
--- a/components/rappor/BUILD.gn
+++ b/components/rappor/BUILD.gn
@@ -38,9 +38,9 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/data_use_measurement/core",
     "//components/metrics",
+    "//components/prefs",
     "//components/variations",
     "//crypto",
     "//net",
@@ -63,7 +63,7 @@
   ]
   deps = [
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
   ]
 }
 
@@ -84,9 +84,9 @@
     ":rappor",
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/metrics",
+    "//components/prefs:test_support",
     "//net:test_support",
     "//testing/gtest",
     "//url",
diff --git a/components/search_engines/BUILD.gn b/components/search_engines/BUILD.gn
index 3229f4b..08b81789 100644
--- a/components/search_engines/BUILD.gn
+++ b/components/search_engines/BUILD.gn
@@ -55,7 +55,6 @@
     ":prepopulated_engines",
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/google/core/browser",
     "//components/history/core/browser",
     "//components/keyed_service/core",
@@ -67,6 +66,7 @@
     # dependency added:
     #"//components/omnibox/browser",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/rappor",
     "//components/strings",
     "//components/sync_driver",
diff --git a/components/security_interstitials/core/BUILD.gn b/components/security_interstitials/core/BUILD.gn
index 6dc2e7b..6595ce9 100644
--- a/components/security_interstitials/core/BUILD.gn
+++ b/components/security_interstitials/core/BUILD.gn
@@ -20,10 +20,10 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/google/core/browser",
     "//components/history/core/browser",
     "//components/metrics",
+    "//components/prefs",
     "//components/rappor",
     "//components/ssl_errors",
     "//components/strings",
diff --git a/components/signin.gypi b/components/signin.gypi
index 5682bd7..5ce36bf 100644
--- a/components/signin.gypi
+++ b/components/signin.gypi
@@ -39,7 +39,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../crypto/crypto.gyp:crypto',
         '../google_apis/google_apis.gyp:google_apis',
         '../net/net.gyp:net',
@@ -54,6 +53,7 @@
         'keyed_service_core',
         'metrics',
         'os_crypt',
+        'prefs/prefs.gyp:prefs',
         'signin_core_common',
         'signin_core_account_id',
         'webdata_common',
diff --git a/components/signin/core/browser/BUILD.gn b/components/signin/core/browser/BUILD.gn
index 1e9766b..32c6353 100644
--- a/components/signin/core/browser/BUILD.gn
+++ b/components/signin/core/browser/BUILD.gn
@@ -75,7 +75,6 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/content_settings/core/browser",
     "//components/content_settings/core/common",
     "//components/google/core/browser",
@@ -84,6 +83,7 @@
     "//components/metrics",
     "//components/os_crypt",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/signin/core/account_id",
     "//components/signin/core/common",
     "//components/webdata/common",
@@ -129,7 +129,7 @@
   public_deps = [
     ":browser",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//components/webdata/common",
     "//google_apis:test_support",
     "//net:test_support",
diff --git a/components/signin/ios/browser/BUILD.gn b/components/signin/ios/browser/BUILD.gn
index 6c4e5e1..d11349b 100644
--- a/components/signin/ios/browser/BUILD.gn
+++ b/components/signin/ios/browser/BUILD.gn
@@ -18,11 +18,11 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/content_settings/core/browser",
     "//components/google/core/browser",
     "//components/keyed_service/core",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/signin/core/browser",
     "//components/signin/core/common",
     "//google_apis",
@@ -56,9 +56,8 @@
 
   deps = [
     ":test_support",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//components/signin/core/browser",
     "//components/signin/core/browser:test_support",
     "//components/signin/core/common",
diff --git a/components/ssl_config.gypi b/components/ssl_config.gypi
index 261b26c8..2e742b21e 100644
--- a/components/ssl_config.gypi
+++ b/components/ssl_config.gypi
@@ -10,10 +10,10 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../net/net.gyp:net',
         'content_settings_core_browser',
         'content_settings_core_common',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/ssl_config/BUILD.gn b/components/ssl_config/BUILD.gn
index 709cb3d..babcc5cb 100644
--- a/components/ssl_config/BUILD.gn
+++ b/components/ssl_config/BUILD.gn
@@ -15,9 +15,9 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/content_settings/core/browser",
     "//components/content_settings/core/common",
+    "//components/prefs",
     "//net",
   ]
 }
@@ -30,7 +30,7 @@
   deps = [
     ":ssl_config",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//net",
     "//testing/gtest",
   ]
diff --git a/components/startup_metric_utils.gypi b/components/startup_metric_utils.gypi
index 05599dca..83ccd89 100644
--- a/components/startup_metric_utils.gypi
+++ b/components/startup_metric_utils.gypi
@@ -14,8 +14,8 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         'components.gyp:version_info',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/startup_metric_utils/browser/BUILD.gn b/components/startup_metric_utils/browser/BUILD.gn
index a56b59fb..7d03b432 100644
--- a/components/startup_metric_utils/browser/BUILD.gn
+++ b/components/startup_metric_utils/browser/BUILD.gn
@@ -25,7 +25,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/version_info",
   ]
 }
diff --git a/components/suggestions/BUILD.gn b/components/suggestions/BUILD.gn
index b9b1aea..4ffad36 100644
--- a/components/suggestions/BUILD.gn
+++ b/components/suggestions/BUILD.gn
@@ -23,7 +23,7 @@
 
   public_deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/suggestions/proto",
     "//net",
     "//ui/gfx",
diff --git a/components/sync_bookmarks/BUILD.gn b/components/sync_bookmarks/BUILD.gn
index 705f3c35..a1eb017 100644
--- a/components/sync_bookmarks/BUILD.gn
+++ b/components/sync_bookmarks/BUILD.gn
@@ -36,10 +36,10 @@
   deps = [
     ":sync_bookmarks",
     "//base",
-    "//base:prefs_test_support",
     "//components/bookmarks/browser",
     "//components/bookmarks/test",
     "//components/history/core/browser",
+    "//components/prefs:test_support",
     "//components/sync_driver",
     "//components/sync_driver:test_support",
     "//sync",
diff --git a/components/sync_driver/BUILD.gn b/components/sync_driver/BUILD.gn
index 49debde..46e586f 100644
--- a/components/sync_driver/BUILD.gn
+++ b/components/sync_driver/BUILD.gn
@@ -124,11 +124,11 @@
   ]
   deps = [
     "//base",
-    "//base:prefs",
     "//base/third_party/dynamic_annotations",
     "//components/data_use_measurement/core",
     "//components/invalidation/public",
     "//components/os_crypt",
+    "//components/prefs",
     "//components/pref_registry",
     "//components/signin/core/browser",
     "//components/version_info",
@@ -230,11 +230,11 @@
   deps = [
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/invalidation/impl",
     "//components/os_crypt",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//components/signin/core/browser:test_support",
     "//components/syncable_prefs",
     "//components/syncable_prefs:test_support",
diff --git a/components/sync_sessions.gypi b/components/sync_sessions.gypi
index 5b0e1a7..c5a22b5 100644
--- a/components/sync_sessions.gypi
+++ b/components/sync_sessions.gypi
@@ -13,11 +13,11 @@
       ],
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../sync/sync.gyp:sync',
         '../url/url.gyp:url_lib',
         'bookmarks_browser',
         'history_core_browser',
+        'prefs/prefs.gyp:prefs',
         'sync_driver',
       ],
       'sources': [
diff --git a/components/sync_sessions/BUILD.gn b/components/sync_sessions/BUILD.gn
index 3f6ceb8..669b7fb 100644
--- a/components/sync_sessions/BUILD.gn
+++ b/components/sync_sessions/BUILD.gn
@@ -49,10 +49,10 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/bookmarks/browser",
     "//components/favicon/core",
     "//components/history/core/browser",
+    "//components/prefs",
     "//components/sessions",
     "//components/sync_driver",
     "//components/variations",
@@ -97,11 +97,10 @@
   deps = [
     ":sync_sessions",
     ":test_support",
-    "//base:prefs",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/bookmarks/browser",
     "//components/history/core/browser",
+    "//components/prefs:test_support",
     "//components/sessions:test_support",
     "//components/sync_driver",
     "//components/sync_driver:test_support",
diff --git a/components/syncable_prefs.gypi b/components/syncable_prefs.gypi
index 7e143a1..e4cfc43 100644
--- a/components/syncable_prefs.gypi
+++ b/components/syncable_prefs.gypi
@@ -10,9 +10,9 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../sync/sync.gyp:sync',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/syncable_prefs/BUILD.gn b/components/syncable_prefs/BUILD.gn
index c854abb..d2c94ac7 100644
--- a/components/syncable_prefs/BUILD.gn
+++ b/components/syncable_prefs/BUILD.gn
@@ -21,8 +21,8 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/pref_registry",
+    "//components/prefs",
     "//sync",
   ]
 
@@ -46,8 +46,8 @@
   deps = [
     ":syncable_prefs",
     "//base",
-    "//base:prefs_test_support",
     "//components/pref_registry",
+    "//components/prefs:test_support",
     "//testing/gtest",
   ]
 }
@@ -62,8 +62,8 @@
   deps = [
     ":syncable_prefs",
     ":test_support",
-    "//base:prefs",
     "//components/pref_registry",
+    "//components/prefs",
     "//sync:test_support_sync_api",
     "//testing/gtest",
   ]
diff --git a/components/translate/core/browser/BUILD.gn b/components/translate/core/browser/BUILD.gn
index d6593fd..d14062c 100644
--- a/components/translate/core/browser/BUILD.gn
+++ b/components/translate/core/browser/BUILD.gn
@@ -42,10 +42,10 @@
   deps = [
     "//base",
     "//base:i18n",
-    "//base:prefs",
     "//components/data_use_measurement/core",
     "//components/language_usage_metrics",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/resources:components_resources",
     "//components/strings",
     "//components/translate/core/common",
@@ -84,8 +84,8 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs",
     "//components/pref_registry:test_support",
+    "//components/prefs",
     "//components/translate/core/common",
     "//net:test_support",
     "//testing/gtest",
diff --git a/components/translate/ios/browser/BUILD.gn b/components/translate/ios/browser/BUILD.gn
index d71d121..1eefbb02 100644
--- a/components/translate/ios/browser/BUILD.gn
+++ b/components/translate/ios/browser/BUILD.gn
@@ -21,7 +21,7 @@
   deps = [
     ":injected_js",
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/translate/core/browser",
     "//components/translate/core/common",
     "//components/translate/core/language_detection",
@@ -50,7 +50,7 @@
   deps = [
     ":browser",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//components/resources",
     "//components/translate/core/common",
     "//ios/web:test_support",
diff --git a/components/ui/zoom/BUILD.gn b/components/ui/zoom/BUILD.gn
index d1d5b00..4a2f3ea 100644
--- a/components/ui/zoom/BUILD.gn
+++ b/components/ui/zoom/BUILD.gn
@@ -18,7 +18,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//content/public/browser",
     "//content/public/common",
     "//ipc",
@@ -47,7 +47,7 @@
   ]
   deps = [
     ":zoom",
-    "//base:prefs",
+    "//components/prefs",
     "//content/public/common",
     "//testing/gtest",
   ]
diff --git a/components/user_manager.gypi b/components/user_manager.gypi
index 3ea388b..9cb57d2 100644
--- a/components/user_manager.gypi
+++ b/components/user_manager.gypi
@@ -51,8 +51,8 @@
     'conditions': [
       ['chromeos == 1', {
         'dependencies': [
-          '<(DEPTH)/base/base.gyp:base_prefs',
           '<(DEPTH)/components/components.gyp:session_manager_component',
+          '<(DEPTH)/components/prefs/prefs.gyp:prefs',
           '<(DEPTH)/google_apis/google_apis.gyp:google_apis',
           '<(DEPTH)/url/url.gyp:url_lib',
         ],
diff --git a/components/user_manager/BUILD.gn b/components/user_manager/BUILD.gn
index 959bcfe..32fbdc2 100644
--- a/components/user_manager/BUILD.gn
+++ b/components/user_manager/BUILD.gn
@@ -38,7 +38,7 @@
       "user_type.h",
     ]
     deps += [
-      "//base:prefs",
+      "//components/prefs",
       "//components/session_manager/core",
       "//google_apis",
       "//url",
diff --git a/components/user_prefs.gypi b/components/user_prefs.gypi
index db5590f..b558435f 100644
--- a/components/user_prefs.gypi
+++ b/components/user_prefs.gypi
@@ -9,7 +9,7 @@
       'type': '<(component)',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/user_prefs/BUILD.gn b/components/user_prefs/BUILD.gn
index 3d777d23..ed09b2d 100644
--- a/components/user_prefs/BUILD.gn
+++ b/components/user_prefs/BUILD.gn
@@ -13,6 +13,6 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
   ]
 }
diff --git a/components/user_prefs/tracked/BUILD.gn b/components/user_prefs/tracked/BUILD.gn
index 25fc09c..8a855eebf 100644
--- a/components/user_prefs/tracked/BUILD.gn
+++ b/components/user_prefs/tracked/BUILD.gn
@@ -54,8 +54,8 @@
 
   deps = [
     "//base:base",
-    "//base:prefs",
     "//components/pref_registry",
+    "//components/prefs",
     "//crypto:crypto",
   ]
 }
@@ -89,8 +89,7 @@
     ":user_prefs_tracked",
     ":user_prefs_tracked_test_support",
     "//base:base",
-    "//base:prefs",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//testing/gtest",
   ]
 }
diff --git a/components/variations.gypi b/components/variations.gypi
index e880638..e67f11f 100644
--- a/components/variations.gypi
+++ b/components/variations.gypi
@@ -15,12 +15,12 @@
         # List of dependencies is intentionally very minimal. Please avoid
         # adding extra dependencies without first checking with OWNERS.
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../crypto/crypto.gyp:crypto',
         '../third_party/mt19937ar/mt19937ar.gyp:mt19937ar',
         '../third_party/protobuf/protobuf.gyp:protobuf_lite',
         '../third_party/zlib/google/zip.gyp:compression_utils',
         'crash_core_common',
+        'prefs/prefs.gyp:prefs',
       ],
       'sources': [
         # Note: sources list duplicated in GN build.
@@ -102,13 +102,13 @@
       ],
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../net/net.gyp:net',
         '../ui/base/ui_base.gyp:ui_base',
         'data_use_measurement_core',
         'metrics',
         'network_time',
         'pref_registry',
+        'prefs/prefs.gyp:prefs',
         'variations',
         'version_info',
         'web_resource',
diff --git a/components/variations/BUILD.gn b/components/variations/BUILD.gn
index 482d400..32c71f22 100644
--- a/components/variations/BUILD.gn
+++ b/components/variations/BUILD.gn
@@ -68,8 +68,8 @@
   deps = [
     "proto",
     "//base",
-    "//base:prefs",
     "//components/crash/core/common",
+    "//components/prefs",
     "//crypto",
     "//third_party/mt19937ar",
     "//third_party/protobuf:protobuf_lite",
@@ -118,8 +118,8 @@
     ":variations",
     "net",
     "proto",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//testing/gtest",
     "//third_party/zlib:compression_utils",
   ]
diff --git a/components/variations/service/BUILD.gn b/components/variations/service/BUILD.gn
index 66fa838c3..099be5c2 100644
--- a/components/variations/service/BUILD.gn
+++ b/components/variations/service/BUILD.gn
@@ -13,11 +13,11 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/data_use_measurement/core",
     "//components/metrics",
     "//components/network_time",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/variations",
     "//components/variations/proto",
     "//components/version_info",
@@ -37,8 +37,8 @@
   deps = [
     ":service",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//components/variations",
     "//components/variations/proto",
     "//components/web_resource:test_support",
diff --git a/components/wallpaper.gypi b/components/wallpaper.gypi
index da83084..350117b 100644
--- a/components/wallpaper.gypi
+++ b/components/wallpaper.gypi
@@ -8,12 +8,12 @@
       'type': '<(component)',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../content/content.gyp:content',
         '../skia/skia.gyp:skia',
         '../ui/gfx/gfx.gyp:gfx',
         '../ui/gfx/gfx.gyp:gfx_geometry',
         '../url/url.gyp:url_lib',
+        'prefs/prefs.gyp:prefs',
       ],
       'include_dirs': [
         '..',
diff --git a/components/wallpaper/BUILD.gn b/components/wallpaper/BUILD.gn
index befd942..04cc0a15 100644
--- a/components/wallpaper/BUILD.gn
+++ b/components/wallpaper/BUILD.gn
@@ -17,7 +17,7 @@
     "//skia",
   ]
   deps = [
-    "//base:prefs",
+    "//components/prefs",
     "//ui/gfx",
     "//ui/gfx/geometry",
     "//url",
diff --git a/components/web_cache/browser/BUILD.gn b/components/web_cache/browser/BUILD.gn
index e64a2d5..25f1d6d 100644
--- a/components/web_cache/browser/BUILD.gn
+++ b/components/web_cache/browser/BUILD.gn
@@ -12,7 +12,7 @@
 
   deps = [
     "//base",
-    "//base:prefs",
+    "//components/prefs",
     "//components/web_cache/common",
     "//content/public/browser",
     "//third_party/WebKit/public:blink",
diff --git a/components/web_resource/BUILD.gn b/components/web_resource/BUILD.gn
index 6c396d9..387a006 100644
--- a/components/web_resource/BUILD.gn
+++ b/components/web_resource/BUILD.gn
@@ -29,9 +29,9 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/google/core/browser",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/version_info",
     "//net",
     "//ui/base",
@@ -66,7 +66,7 @@
     ":test_support",
     ":web_resource",
     "//base",
-    "//base:prefs_test_support",
+    "//components/prefs:test_support",
     "//components/version_info",
     "//net:test_support",
     "//testing/gtest",
diff --git a/content/test/gpu/generate_buildbot_json.py b/content/test/gpu/generate_buildbot_json.py
index ea6661c..a1d1354 100755
--- a/content/test/gpu/generate_buildbot_json.py
+++ b/content/test/gpu/generate_buildbot_json.py
@@ -433,6 +433,9 @@
   'screenshot_sync': {},
   'trace_test': {},
   'webgl_conformance': {},
+}
+
+FYI_ONLY_TELEMETRY_TESTS = {
   'webgl_conformance_d3d9_tests': {
     'win_only': True,
     'target_name': 'webgl_conformance',
@@ -561,6 +564,14 @@
       gtests.append(test)
   return gtests
 
+def generate_telemetry_tests(tester_config, test_dictionary):
+  isolated_scripts = []
+  for test_name, test_config in sorted(test_dictionary.iteritems()):
+    test = generate_telemetry_test(tester_config, test_name, test_config)
+    if test:
+      isolated_scripts.append(test)
+  return isolated_scripts
+
 def generate_all_tests(waterfall, is_fyi):
   tests = {}
   for builder in waterfall['builders']:
@@ -577,10 +588,10 @@
         gtests.extend(generate_gtests(config, FYI_ONLY_GTESTS))
     isolated_scripts = []
     if not config.get('deqp'):
-      for test_name, test_config in sorted(TELEMETRY_TESTS.iteritems()):
-        test = generate_telemetry_test(config, test_name, test_config)
-        if test:
-          isolated_scripts.append(test)
+      isolated_scripts.extend(generate_telemetry_tests(config, TELEMETRY_TESTS))
+      if is_fyi:
+        isolated_scripts.extend(generate_telemetry_tests(
+            config, FYI_ONLY_TELEMETRY_TESTS))
     cur_tests = {}
     if gtests:
       cur_tests['gtest_tests'] = sorted(gtests, key=lambda x: x['test'])
diff --git a/extensions/BUILD.gn b/extensions/BUILD.gn
index ad2ea80..45db1d744 100644
--- a/extensions/BUILD.gn
+++ b/extensions/BUILD.gn
@@ -81,9 +81,9 @@
   deps = [
     ":extensions_resources",
     "//base",
-    "//base:prefs_test_support",
     "//components/guest_view/browser:test_support",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//content/public/common",
     "//content/test:test_support",
     "//extensions/browser",
@@ -175,10 +175,10 @@
     ":shell_and_test_pak",
     ":test_support",
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/keyed_service/content",
     "//components/pref_registry:test_support",
+    "//components/prefs:test_support",
     "//components/user_prefs",
     "//content/test:test_support",
     "//device/bluetooth:mocks",
@@ -251,8 +251,8 @@
 
     # TODO(yoz): find the right deps
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
+    "//components/prefs:test_support",
     "//components/storage_monitor:test_support",
     "//content/test:test_support",
     "//device/bluetooth:mocks",
diff --git a/extensions/extensions.gyp b/extensions/extensions.gyp
index ad0b6bf..59ee0072 100644
--- a/extensions/extensions.gyp
+++ b/extensions/extensions.gyp
@@ -107,7 +107,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs',
         '../components/components.gyp:browsing_data',
         '../components/components.gyp:device_event_log_component',
         '../components/components.gyp:guest_view_browser',
@@ -123,6 +122,7 @@
         '../components/components.gyp:version_info',
         '../components/components.gyp:web_cache_browser',
         '../components/components.gyp:web_modal',
+        '../components/prefs/prefs.gyp:prefs',
         '../content/content.gyp:content_browser',
         '../device/bluetooth/bluetooth.gyp:device_bluetooth',
         '../device/serial/serial.gyp:device_serial',
@@ -248,9 +248,9 @@
       'type': 'static_library',
       'dependencies': [
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs_test_support',
         '../components/components.gyp:pref_registry_test_support',
         '../components/components.gyp:user_prefs',
+        '../components/prefs/prefs.gyp:prefs_test_support',
         '../content/content.gyp:content_browser',
         '../content/content.gyp:content_common',
         '../content/content_shell_and_tests.gyp:test_support_content',
diff --git a/extensions/shell/BUILD.gn b/extensions/shell/BUILD.gn
index fbc8b9b6..52e3cabe 100644
--- a/extensions/shell/BUILD.gn
+++ b/extensions/shell/BUILD.gn
@@ -30,13 +30,13 @@
     ":resources",
     ":version_header",
     "//base",
-    "//base:prefs",
     "//components/devtools_discovery",
     "//components/devtools_http_handler",
     "//components/guest_view/browser",
     "//components/guest_view/common",
     "//components/guest_view/renderer",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/update_client",
     "//components/user_prefs",
     "//components/web_cache/renderer",
diff --git a/extensions/shell/app_shell.gyp b/extensions/shell/app_shell.gyp
index 10594be..695bb32 100644
--- a/extensions/shell/app_shell.gyp
+++ b/extensions/shell/app_shell.gyp
@@ -22,13 +22,13 @@
       'dependencies': [
         'app_shell_version_header',
         '<(DEPTH)/base/base.gyp:base',
-        '<(DEPTH)/base/base.gyp:base_prefs',
         '<(DEPTH)/components/components.gyp:devtools_discovery',
         '<(DEPTH)/components/components.gyp:devtools_http_handler',
         '<(DEPTH)/components/components.gyp:pref_registry',
         '<(DEPTH)/components/components.gyp:update_client',
         '<(DEPTH)/components/components.gyp:user_prefs',
         '<(DEPTH)/components/components.gyp:web_cache_renderer',
+        '<(DEPTH)/components/prefs/prefs.gyp:prefs',
         '<(DEPTH)/content/content.gyp:content',
         '<(DEPTH)/content/content.gyp:content_browser',
         '<(DEPTH)/content/content.gyp:content_gpu',
diff --git a/ios/chrome/BUILD.gn b/ios/chrome/BUILD.gn
index 1f7355f8..6145aef 100644
--- a/ios/chrome/BUILD.gn
+++ b/ios/chrome/BUILD.gn
@@ -42,12 +42,12 @@
 
   deps = [
     "//base",
-    "//base:prefs_test_support",
     "//base/test:test_support",
     "//components/bookmarks/test",
     "//components/favicon_base",
     "//components/metrics",
     "//components/metrics:test_support",
+    "//components/prefs:test_support",
     "//components/signin/core/browser:test_support",
     "//components/signin/ios/browser:test_support",
     "//components/sync_driver:test_support",
diff --git a/ios/chrome/browser/BUILD.gn b/ios/chrome/browser/BUILD.gn
index 8c467746..cea1de69 100644
--- a/ios/chrome/browser/BUILD.gn
+++ b/ios/chrome/browser/BUILD.gn
@@ -498,7 +498,6 @@
     ":about_flags",
     ":injected_js",
     "//base",
-    "//base:prefs",
     "//breakpad:client",
     "//components/about_handler",
     "//components/autofill/core/browser",
@@ -544,6 +543,7 @@
     "//components/password_manager/sync/browser",
     "//components/policy:policy_component_common",
     "//components/pref_registry",
+    "//components/prefs",
     "//components/profile_metrics",
     "//components/proxy_config",
     "//components/rappor",
diff --git a/ios/chrome/ios_chrome.gyp b/ios/chrome/ios_chrome.gyp
index 5d0749d..2c918ab 100644
--- a/ios/chrome/ios_chrome.gyp
+++ b/ios/chrome/ios_chrome.gyp
@@ -44,7 +44,6 @@
       ],
       'dependencies': [
         '../../base/base.gyp:base',
-        '../../base/base.gyp:base_prefs',
         '../../breakpad/breakpad.gyp:breakpad_client',
         '../../components/components.gyp:language_usage_metrics',
         '../../components/components.gyp:about_handler',
@@ -118,6 +117,7 @@
         '../../components/components.gyp:webp_transcode',
         '../../components/components_resources.gyp:components_resources',
         '../../components/components_strings.gyp:components_strings',
+        '../../components/prefs/prefs.gyp:prefs',
         '../../components/url_formatter/url_formatter.gyp:url_formatter',
         '../../google_apis/google_apis.gyp:google_apis',
         '../../net/net.gyp:net',
diff --git a/ios/chrome/ios_chrome_tests.gyp b/ios/chrome/ios_chrome_tests.gyp
index d78bfc1..284d874 100644
--- a/ios/chrome/ios_chrome_tests.gyp
+++ b/ios/chrome/ios_chrome_tests.gyp
@@ -12,7 +12,6 @@
       'type': '<(gtest_target_type)',
       'dependencies': [
         '../../base/base.gyp:base',
-        '../../base/base.gyp:base_prefs_test_support',
         '../../base/base.gyp:test_support_base',
         '../../components/components.gyp:bookmarks_test_support',
         '../../components/components.gyp:favicon_base',
@@ -20,6 +19,7 @@
         '../../components/components.gyp:metrics_test_support',
         '../../components/components.gyp:update_client',
         '../../components/components.gyp:version_info',
+        '../../components/prefs/prefs.gyp:prefs_test_support',
         '../../net/net.gyp:net_test_support',
         '../../skia/skia.gyp:skia',
         '../../testing/gmock.gyp:gmock',
diff --git a/ios/chrome/test/BUILD.gn b/ios/chrome/test/BUILD.gn
index 8be284b..fe3d023 100644
--- a/ios/chrome/test/BUILD.gn
+++ b/ios/chrome/test/BUILD.gn
@@ -20,8 +20,8 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/network_time",
+    "//components/prefs",
     "//ios/chrome/browser",
     "//ios/public/provider/chrome/browser",
     "//ios/public/test",
diff --git a/ios/crnet/crnet.gyp b/ios/crnet/crnet.gyp
index b5eb9c1..7908255 100644
--- a/ios/crnet/crnet.gyp
+++ b/ios/crnet/crnet.gyp
@@ -12,6 +12,7 @@
       'type': 'static_library',
       'dependencies': [
         '../../components/components.gyp:webp_transcode',
+        '../../components/prefs/prefs.gyp:prefs',
         '../../ios/net/ios_net.gyp:ios_net',
         '../../ios/web/ios_web.gyp:user_agent',
         '../../net/net.gyp:net',
diff --git a/mash/wallpaper/BUILD.gn b/mash/wallpaper/BUILD.gn
index 26cad0f0..00232e6 100644
--- a/mash/wallpaper/BUILD.gn
+++ b/mash/wallpaper/BUILD.gn
@@ -13,11 +13,11 @@
 
   deps = [
     "//base",
-    "//base:prefs",
     "//components/filesystem/public/cpp/prefs",
     "//components/filesystem/public/interfaces",
     "//components/mus/public/cpp",
     "//components/mus/public/interfaces",
+    "//components/prefs",
     "//mash/wm/public/interfaces",
     "//mojo/public/cpp/bindings",
     "//mojo/services/tracing/public/cpp",
diff --git a/net/BUILD.gn b/net/BUILD.gn
index 56525c6..102c703 100644
--- a/net/BUILD.gn
+++ b/net/BUILD.gn
@@ -122,8 +122,8 @@
   net_shared_sources += gypi_values.net_non_nacl_sources
 
   net_shared_deps += [
-    "//base:prefs",
     "//base/third_party/dynamic_annotations",
+    "//components/prefs",
     "//sdch",
     "//third_party/zlib",
   ]
@@ -1407,7 +1407,6 @@
     ":test_support",
     "//base",
     "//base:i18n",
-    "//base:prefs_test_support",
     "//base/third_party/dynamic_annotations",
     "//crypto",
     "//crypto:platform",
diff --git a/net/net.gyp b/net/net.gyp
index 68a4cc0..2222d3e0 100644
--- a/net/net.gyp
+++ b/net/net.gyp
@@ -142,7 +142,6 @@
       'dependencies': [
         '../base/base.gyp:base',
         '../base/base.gyp:base_i18n',
-        '../base/base.gyp:base_prefs_test_support',
         '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
         '../crypto/crypto.gyp:crypto',
         '../crypto/crypto.gyp:crypto_test_support',
diff --git a/net/net_common.gypi b/net/net_common.gypi
index fe14edd..1b4f45a 100644
--- a/net/net_common.gypi
+++ b/net/net_common.gypi
@@ -8,7 +8,6 @@
   'variables': { 'enable_wexit_time_destructors': 1, },
   'dependencies': [
     '../base/base.gyp:base',
-    '../base/base.gyp:base_prefs',
     '../base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
     '../crypto/crypto.gyp:crypto',
     '../sdch/sdch.gyp:sdch',
diff --git a/remoting/protocol/audio_reader.cc b/remoting/protocol/audio_reader.cc
index d197a83..e7511f6d8 100644
--- a/remoting/protocol/audio_reader.cc
+++ b/remoting/protocol/audio_reader.cc
@@ -7,6 +7,9 @@
 #include "base/bind.h"
 #include "net/socket/stream_socket.h"
 #include "remoting/base/constants.h"
+#include "remoting/proto/audio.pb.h"
+#include "remoting/protocol/audio_stub.h"
+#include "remoting/protocol/message_serialization.h"
 #include "remoting/protocol/session.h"
 #include "remoting/protocol/session_config.h"
 
@@ -14,16 +17,17 @@
 namespace protocol {
 
 AudioReader::AudioReader(AudioStub* audio_stub)
-    : ChannelDispatcherBase(kAudioChannelName),
-      audio_stub_(audio_stub),
-      parser_(base::Bind(&AudioReader::OnAudioPacket, base::Unretained(this)),
-              reader()) {}
+    : ChannelDispatcherBase(kAudioChannelName), audio_stub_(audio_stub) {}
 
 AudioReader::~AudioReader() {}
 
-void AudioReader::OnAudioPacket(scoped_ptr<AudioPacket> audio_packet) {
-  audio_stub_->ProcessAudioPacket(std::move(audio_packet),
-                                  base::Bind(&base::DoNothing));
+void AudioReader::OnIncomingMessage(scoped_ptr<CompoundBuffer> message) {
+  scoped_ptr<AudioPacket> audio_packet =
+      ParseMessage<AudioPacket>(message.get());
+  if (audio_packet) {
+    audio_stub_->ProcessAudioPacket(std::move(audio_packet),
+                                    base::Bind(&base::DoNothing));
+  }
 }
 
 }  // namespace protocol
diff --git a/remoting/protocol/audio_reader.h b/remoting/protocol/audio_reader.h
index c20ab5c..4ad5ef9 100644
--- a/remoting/protocol/audio_reader.h
+++ b/remoting/protocol/audio_reader.h
@@ -7,24 +7,22 @@
 
 #include "base/compiler_specific.h"
 #include "base/macros.h"
-#include "remoting/proto/audio.pb.h"
-#include "remoting/protocol/audio_stub.h"
 #include "remoting/protocol/channel_dispatcher_base.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 
 namespace remoting {
 namespace protocol {
 
+class AudioStub;
+
 class AudioReader : public ChannelDispatcherBase {
  public:
   explicit AudioReader(AudioStub* audio_stub);
   ~AudioReader() override;
 
  private:
-  void OnAudioPacket(scoped_ptr<AudioPacket> audio_packet);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
 
   AudioStub* audio_stub_;
-  ProtobufMessageParser<AudioPacket> parser_;
 
   DISALLOW_COPY_AND_ASSIGN(AudioReader);
 };
diff --git a/remoting/protocol/audio_writer.cc b/remoting/protocol/audio_writer.cc
index be60d2e6..3ab624b 100644
--- a/remoting/protocol/audio_writer.cc
+++ b/remoting/protocol/audio_writer.cc
@@ -34,5 +34,9 @@
   return make_scoped_ptr(new AudioWriter());
 }
 
+void AudioWriter::OnIncomingMessage(scoped_ptr<CompoundBuffer> message) {
+  LOG(ERROR) << "Received unexpected message on the audio channel.";
+}
+
 }  // namespace protocol
 }  // namespace remoting
diff --git a/remoting/protocol/audio_writer.h b/remoting/protocol/audio_writer.h
index da591df..89de056 100644
--- a/remoting/protocol/audio_writer.h
+++ b/remoting/protocol/audio_writer.h
@@ -40,6 +40,8 @@
  private:
   AudioWriter();
 
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
+
   DISALLOW_COPY_AND_ASSIGN(AudioWriter);
 };
 
diff --git a/remoting/protocol/channel_dispatcher_base.cc b/remoting/protocol/channel_dispatcher_base.cc
index cd0823b..7679460 100644
--- a/remoting/protocol/channel_dispatcher_base.cc
+++ b/remoting/protocol/channel_dispatcher_base.cc
@@ -47,6 +47,8 @@
       base::Bind(&ChannelDispatcherBase::OnReadWriteFailed,
                  base::Unretained(this)));
   reader_.StartReading(channel_.get(),
+                       base::Bind(&ChannelDispatcherBase::OnIncomingMessage,
+                                  base::Unretained(this)),
                        base::Bind(&ChannelDispatcherBase::OnReadWriteFailed,
                                   base::Unretained(this)));
 
diff --git a/remoting/protocol/channel_dispatcher_base.h b/remoting/protocol/channel_dispatcher_base.h
index 06d2c79..eca2d12d 100644
--- a/remoting/protocol/channel_dispatcher_base.h
+++ b/remoting/protocol/channel_dispatcher_base.h
@@ -55,7 +55,9 @@
   explicit ChannelDispatcherBase(const char* channel_name);
 
   BufferedSocketWriter* writer() { return &writer_; }
-  MessageReader* reader() { return &reader_; }
+
+  // Child classes must override this method to handle incoming messages.
+  virtual void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) = 0;
 
  private:
   void OnChannelReady(scoped_ptr<P2PStreamSocket> socket);
diff --git a/remoting/protocol/channel_multiplexer.cc b/remoting/protocol/channel_multiplexer.cc
index 65d29c0..1ac07ffd 100644
--- a/remoting/protocol/channel_multiplexer.cc
+++ b/remoting/protocol/channel_multiplexer.cc
@@ -305,11 +305,7 @@
     : base_channel_factory_(factory),
       base_channel_name_(base_channel_name),
       next_channel_id_(0),
-      parser_(base::Bind(&ChannelMultiplexer::OnIncomingPacket,
-                         base::Unretained(this)),
-              &reader_),
-      weak_factory_(this) {
-}
+      weak_factory_(this) {}
 
 ChannelMultiplexer::~ChannelMultiplexer() {
   DCHECK(pending_channels_.empty());
@@ -361,6 +357,8 @@
   if (base_channel_.get()) {
     // Initialize reader and writer.
     reader_.StartReading(base_channel_.get(),
+                         base::Bind(&ChannelMultiplexer::OnIncomingPacket,
+                                    base::Unretained(this)),
                          base::Bind(&ChannelMultiplexer::OnBaseChannelError,
                                     base::Unretained(this)));
     writer_.Start(base::Bind(&P2PStreamSocket::Write,
@@ -424,7 +422,12 @@
     it->second->OnBaseChannelError(error);
 }
 
-void ChannelMultiplexer::OnIncomingPacket(scoped_ptr<MultiplexPacket> packet) {
+void ChannelMultiplexer::OnIncomingPacket(scoped_ptr<CompoundBuffer> buffer) {
+  scoped_ptr<MultiplexPacket> packet =
+      ParseMessage<MultiplexPacket>(buffer.get());
+  if (!packet)
+    return;
+
   DCHECK(packet->has_channel_id());
   if (!packet->has_channel_id()) {
     LOG(ERROR) << "Received packet without channel_id.";
diff --git a/remoting/protocol/channel_multiplexer.h b/remoting/protocol/channel_multiplexer.h
index 694e08a0..976561c0 100644
--- a/remoting/protocol/channel_multiplexer.h
+++ b/remoting/protocol/channel_multiplexer.h
@@ -10,7 +10,6 @@
 #include "remoting/base/buffered_socket_writer.h"
 #include "remoting/proto/mux.pb.h"
 #include "remoting/protocol/message_reader.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 #include "remoting/protocol/stream_channel_factory.h"
 
 namespace remoting {
@@ -53,7 +52,7 @@
   void NotifyBaseChannelError(const std::string& name, int error);
 
   // Callback for |reader_;
-  void OnIncomingPacket(scoped_ptr<MultiplexPacket> packet);
+  void OnIncomingPacket(scoped_ptr<CompoundBuffer> buffer);
 
   // Called by MuxChannel.
   void DoWrite(scoped_ptr<MultiplexPacket> packet,
@@ -81,7 +80,6 @@
 
   BufferedSocketWriter writer_;
   MessageReader reader_;
-  ProtobufMessageParser<MultiplexPacket> parser_;
 
   base::WeakPtrFactory<ChannelMultiplexer> weak_factory_;
 
diff --git a/remoting/protocol/client_control_dispatcher.cc b/remoting/protocol/client_control_dispatcher.cc
index 3ce2f95..6ee4256 100644
--- a/remoting/protocol/client_control_dispatcher.cc
+++ b/remoting/protocol/client_control_dispatcher.cc
@@ -59,13 +59,7 @@
 }  // namespace
 
 ClientControlDispatcher::ClientControlDispatcher()
-    : ChannelDispatcherBase(kControlChannelName),
-      client_stub_(nullptr),
-      clipboard_stub_(nullptr),
-      parser_(base::Bind(&ClientControlDispatcher::OnMessageReceived,
-                         base::Unretained(this)),
-              reader()) {}
-
+    : ChannelDispatcherBase(kControlChannelName) {}
 ClientControlDispatcher::~ClientControlDispatcher() {}
 
 void ClientControlDispatcher::InjectClipboardEvent(
@@ -115,11 +109,16 @@
   writer()->Write(SerializeAndFrameMessage(control_message), base::Closure());
 }
 
-void ClientControlDispatcher::OnMessageReceived(
-    scoped_ptr<ControlMessage> message) {
+void ClientControlDispatcher::OnIncomingMessage(
+    scoped_ptr<CompoundBuffer> buffer) {
   DCHECK(client_stub_);
   DCHECK(clipboard_stub_);
 
+  scoped_ptr<ControlMessage> message =
+      ParseMessage<ControlMessage>(buffer.get());
+  if (!message)
+    return;
+
   if (message->has_clipboard_event()) {
     clipboard_stub_->InjectClipboardEvent(message->clipboard_event());
   } else if (message->has_capabilities()) {
diff --git a/remoting/protocol/client_control_dispatcher.h b/remoting/protocol/client_control_dispatcher.h
index 6e9b46e..c646fe5 100644
--- a/remoting/protocol/client_control_dispatcher.h
+++ b/remoting/protocol/client_control_dispatcher.h
@@ -11,7 +11,6 @@
 #include "remoting/protocol/clipboard_stub.h"
 #include "remoting/protocol/cursor_shape_stub.h"
 #include "remoting/protocol/host_stub.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 
 namespace remoting {
 namespace protocol {
@@ -52,12 +51,10 @@
   }
 
  private:
-  void OnMessageReceived(scoped_ptr<ControlMessage> message);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
 
-  ClientStub* client_stub_;
-  ClipboardStub* clipboard_stub_;
-
-  ProtobufMessageParser<ControlMessage> parser_;
+  ClientStub* client_stub_ = nullptr;
+  ClipboardStub* clipboard_stub_ = nullptr;
 
   DISALLOW_COPY_AND_ASSIGN(ClientControlDispatcher);
 };
diff --git a/remoting/protocol/client_event_dispatcher.cc b/remoting/protocol/client_event_dispatcher.cc
index 9329227b..87ae9b3 100644
--- a/remoting/protocol/client_event_dispatcher.cc
+++ b/remoting/protocol/client_event_dispatcher.cc
@@ -52,5 +52,10 @@
   writer()->Write(SerializeAndFrameMessage(message), base::Closure());
 }
 
+void ClientEventDispatcher::OnIncomingMessage(
+    scoped_ptr<CompoundBuffer> message) {
+  LOG(ERROR) << "Received unexpected message on the event channel.";
+}
+
 }  // namespace protocol
 }  // namespace remoting
diff --git a/remoting/protocol/client_event_dispatcher.h b/remoting/protocol/client_event_dispatcher.h
index 97c6b041..98d4473 100644
--- a/remoting/protocol/client_event_dispatcher.h
+++ b/remoting/protocol/client_event_dispatcher.h
@@ -27,6 +27,8 @@
   void InjectTouchEvent(const TouchEvent& event) override;
 
  private:
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
+
   DISALLOW_COPY_AND_ASSIGN(ClientEventDispatcher);
 };
 
diff --git a/remoting/protocol/client_video_dispatcher.cc b/remoting/protocol/client_video_dispatcher.cc
index e913700f..f82b7bd 100644
--- a/remoting/protocol/client_video_dispatcher.cc
+++ b/remoting/protocol/client_video_dispatcher.cc
@@ -28,15 +28,16 @@
 ClientVideoDispatcher::ClientVideoDispatcher(VideoStub* video_stub)
     : ChannelDispatcherBase(kVideoChannelName),
       video_stub_(video_stub),
-      parser_(base::Bind(&ClientVideoDispatcher::ProcessVideoPacket,
-                         base::Unretained(this)),
-              reader()),
       weak_factory_(this) {}
-
 ClientVideoDispatcher::~ClientVideoDispatcher() {}
 
-void ClientVideoDispatcher::ProcessVideoPacket(
-    scoped_ptr<VideoPacket> video_packet) {
+void ClientVideoDispatcher::OnIncomingMessage(
+    scoped_ptr<CompoundBuffer> message) {
+  scoped_ptr<VideoPacket> video_packet =
+      ParseMessage<VideoPacket>(message.get());
+  if (!video_packet)
+    return;
+
   int frame_id = video_packet->frame_id();
 
   if (!video_packet->has_frame_id()) {
diff --git a/remoting/protocol/client_video_dispatcher.h b/remoting/protocol/client_video_dispatcher.h
index 98fea75..39efda200 100644
--- a/remoting/protocol/client_video_dispatcher.h
+++ b/remoting/protocol/client_video_dispatcher.h
@@ -10,7 +10,6 @@
 #include "base/memory/weak_ptr.h"
 #include "remoting/proto/video.pb.h"
 #include "remoting/protocol/channel_dispatcher_base.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 
 namespace remoting {
 namespace protocol {
@@ -26,7 +25,7 @@
   struct PendingFrame;
   typedef std::list<PendingFrame> PendingFramesList;
 
-  void ProcessVideoPacket(scoped_ptr<VideoPacket> video_packet);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
 
   // Callback for VideoStub::ProcessVideoPacket().
   void OnPacketDone(PendingFramesList::iterator pending_frame);
@@ -34,7 +33,6 @@
   PendingFramesList pending_frames_;
 
   VideoStub* video_stub_;
-  ProtobufMessageParser<VideoPacket> parser_;
 
   base::WeakPtrFactory<ClientVideoDispatcher> weak_factory_;
 
diff --git a/remoting/protocol/client_video_dispatcher_unittest.cc b/remoting/protocol/client_video_dispatcher_unittest.cc
index 732fecbf..bc31d1a7 100644
--- a/remoting/protocol/client_video_dispatcher_unittest.cc
+++ b/remoting/protocol/client_video_dispatcher_unittest.cc
@@ -35,7 +35,7 @@
                       ErrorCode error) override;
 
  protected:
-  void OnVideoAck(scoped_ptr<VideoAck> ack);
+  void OnMessageReceived(scoped_ptr<CompoundBuffer> buffer);
   void OnReadError(int error);
 
   base::MessageLoop message_loop_;
@@ -50,7 +50,6 @@
   // Host side.
   FakeStreamSocket host_socket_;
   MessageReader reader_;
-  ProtobufMessageParser<VideoAck> parser_;
   BufferedSocketWriter writer_;
 
   ScopedVector<VideoPacket> video_packets_;
@@ -61,16 +60,15 @@
 
 ClientVideoDispatcherTest::ClientVideoDispatcherTest()
     : initialized_(false),
-      dispatcher_(this),
-      parser_(base::Bind(&ClientVideoDispatcherTest::OnVideoAck,
-                         base::Unretained(this)),
-              &reader_) {
+      dispatcher_(this) {
   dispatcher_.Init(&client_channel_factory_, this);
   base::RunLoop().RunUntilIdle();
   DCHECK(initialized_);
   host_socket_.PairWith(
       client_channel_factory_.GetFakeChannel(kVideoChannelName));
   reader_.StartReading(&host_socket_,
+                       base::Bind(&ClientVideoDispatcherTest::OnMessageReceived,
+                                  base::Unretained(this)),
                        base::Bind(&ClientVideoDispatcherTest::OnReadError,
                                   base::Unretained(this)));
   writer_.Start(
@@ -97,7 +95,10 @@
   FAIL();
 }
 
-void ClientVideoDispatcherTest::OnVideoAck(scoped_ptr<VideoAck> ack) {
+void ClientVideoDispatcherTest::OnMessageReceived(
+    scoped_ptr<CompoundBuffer> buffer) {
+  scoped_ptr<VideoAck> ack = ParseMessage<VideoAck>(buffer.get());
+  EXPECT_TRUE(ack);
   ack_messages_.push_back(ack.release());
 }
 
diff --git a/remoting/protocol/host_control_dispatcher.cc b/remoting/protocol/host_control_dispatcher.cc
index 2b067d74c..fb8aee9 100644
--- a/remoting/protocol/host_control_dispatcher.cc
+++ b/remoting/protocol/host_control_dispatcher.cc
@@ -17,16 +17,8 @@
 namespace protocol {
 
 HostControlDispatcher::HostControlDispatcher()
-    : ChannelDispatcherBase(kControlChannelName),
-      clipboard_stub_(nullptr),
-      host_stub_(nullptr),
-      parser_(base::Bind(&HostControlDispatcher::OnMessageReceived,
-                         base::Unretained(this)),
-              reader()) {
-}
-
-HostControlDispatcher::~HostControlDispatcher() {
-}
+    : ChannelDispatcherBase(kControlChannelName) {}
+HostControlDispatcher::~HostControlDispatcher() {}
 
 void HostControlDispatcher::SetCapabilities(
     const Capabilities& capabilities) {
@@ -62,11 +54,16 @@
   writer()->Write(SerializeAndFrameMessage(message), base::Closure());
 }
 
-void HostControlDispatcher::OnMessageReceived(
-    scoped_ptr<ControlMessage> message) {
+void HostControlDispatcher::OnIncomingMessage(
+    scoped_ptr<CompoundBuffer> buffer) {
   DCHECK(clipboard_stub_);
   DCHECK(host_stub_);
 
+  scoped_ptr<ControlMessage> message =
+      ParseMessage<ControlMessage>(buffer.get());
+  if (!message)
+    return;
+
   if (message->has_clipboard_event()) {
     clipboard_stub_->InjectClipboardEvent(message->clipboard_event());
   } else if (message->has_client_resolution()) {
diff --git a/remoting/protocol/host_control_dispatcher.h b/remoting/protocol/host_control_dispatcher.h
index d863f64..5bd7df6 100644
--- a/remoting/protocol/host_control_dispatcher.h
+++ b/remoting/protocol/host_control_dispatcher.h
@@ -10,7 +10,6 @@
 #include "remoting/protocol/client_stub.h"
 #include "remoting/protocol/clipboard_stub.h"
 #include "remoting/protocol/cursor_shape_stub.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 
 namespace net {
 class StreamSocket;
@@ -19,7 +18,6 @@
 namespace remoting {
 namespace protocol {
 
-class ControlMessage;
 class HostStub;
 class PairingResponse;
 class Session;
@@ -55,12 +53,10 @@
   void set_host_stub(HostStub* host_stub) { host_stub_ = host_stub; }
 
  private:
-  void OnMessageReceived(scoped_ptr<ControlMessage> message);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> buffer) override;
 
-  ClipboardStub* clipboard_stub_;
-  HostStub* host_stub_;
-
-  ProtobufMessageParser<ControlMessage> parser_;
+  ClipboardStub* clipboard_stub_ = nullptr;
+  HostStub* host_stub_ = nullptr;
 
   DISALLOW_COPY_AND_ASSIGN(HostControlDispatcher);
 };
diff --git a/remoting/protocol/host_event_dispatcher.cc b/remoting/protocol/host_event_dispatcher.cc
index 36fccc7..d67f651 100644
--- a/remoting/protocol/host_event_dispatcher.cc
+++ b/remoting/protocol/host_event_dispatcher.cc
@@ -9,22 +9,22 @@
 #include "remoting/proto/event.pb.h"
 #include "remoting/proto/internal.pb.h"
 #include "remoting/protocol/input_stub.h"
+#include "remoting/protocol/message_serialization.h"
 
 namespace remoting {
 namespace protocol {
 
 HostEventDispatcher::HostEventDispatcher()
-    : ChannelDispatcherBase(kEventChannelName),
-      input_stub_(nullptr),
-      parser_(base::Bind(&HostEventDispatcher::OnMessageReceived,
-                         base::Unretained(this)),
-              reader()) {}
-
+    : ChannelDispatcherBase(kEventChannelName) {}
 HostEventDispatcher::~HostEventDispatcher() {}
 
-void HostEventDispatcher::OnMessageReceived(scoped_ptr<EventMessage> message) {
+void HostEventDispatcher::OnIncomingMessage(scoped_ptr<CompoundBuffer> buffer) {
   DCHECK(input_stub_);
 
+  scoped_ptr<EventMessage> message = ParseMessage<EventMessage>(buffer.get());
+  if (!message)
+    return;
+
   if (!on_input_event_callback_.is_null())
     on_input_event_callback_.Run(message->timestamp());
 
diff --git a/remoting/protocol/host_event_dispatcher.h b/remoting/protocol/host_event_dispatcher.h
index 9a6211a..e299c2c 100644
--- a/remoting/protocol/host_event_dispatcher.h
+++ b/remoting/protocol/host_event_dispatcher.h
@@ -9,7 +9,6 @@
 
 #include "base/macros.h"
 #include "remoting/protocol/channel_dispatcher_base.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 
 namespace remoting {
 namespace protocol {
@@ -38,13 +37,11 @@
   }
 
  private:
-  void OnMessageReceived(scoped_ptr<EventMessage> message);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> buffer) override;
 
-  InputStub* input_stub_;
+  InputStub* input_stub_ = nullptr;
   OnInputEventCallback on_input_event_callback_;
 
-  ProtobufMessageParser<EventMessage> parser_;
-
   DISALLOW_COPY_AND_ASSIGN(HostEventDispatcher);
 };
 
diff --git a/remoting/protocol/host_video_dispatcher.cc b/remoting/protocol/host_video_dispatcher.cc
index 0d7c0de..ca9b634 100644
--- a/remoting/protocol/host_video_dispatcher.cc
+++ b/remoting/protocol/host_video_dispatcher.cc
@@ -9,6 +9,7 @@
 #include "base/bind.h"
 #include "net/socket/stream_socket.h"
 #include "remoting/base/constants.h"
+#include "remoting/proto/video.pb.h"
 #include "remoting/protocol/message_serialization.h"
 #include "remoting/protocol/video_feedback_stub.h"
 
@@ -16,12 +17,7 @@
 namespace protocol {
 
 HostVideoDispatcher::HostVideoDispatcher()
-    : ChannelDispatcherBase(kVideoChannelName),
-      parser_(
-          base::Bind(&HostVideoDispatcher::OnVideoAck, base::Unretained(this)),
-          reader()),
-      video_feedback_stub_(nullptr) {}
-
+    : ChannelDispatcherBase(kVideoChannelName) {}
 HostVideoDispatcher::~HostVideoDispatcher() {}
 
 void HostVideoDispatcher::ProcessVideoPacket(scoped_ptr<VideoPacket> packet,
@@ -29,7 +25,11 @@
   writer()->Write(SerializeAndFrameMessage(*packet), done);
 }
 
-void HostVideoDispatcher::OnVideoAck(scoped_ptr<VideoAck> ack) {
+void HostVideoDispatcher::OnIncomingMessage(
+    scoped_ptr<CompoundBuffer> message) {
+  scoped_ptr<VideoAck> ack = ParseMessage<VideoAck>(message.get());
+  if (!ack)
+    return;
   if (video_feedback_stub_)
     video_feedback_stub_->ProcessVideoAck(std::move(ack));
 }
diff --git a/remoting/protocol/host_video_dispatcher.h b/remoting/protocol/host_video_dispatcher.h
index 323ddb7..1e61540 100644
--- a/remoting/protocol/host_video_dispatcher.h
+++ b/remoting/protocol/host_video_dispatcher.h
@@ -7,9 +7,7 @@
 
 #include "base/compiler_specific.h"
 #include "base/macros.h"
-#include "remoting/proto/video.pb.h"
 #include "remoting/protocol/channel_dispatcher_base.h"
-#include "remoting/protocol/protobuf_message_parser.h"
 #include "remoting/protocol/video_stub.h"
 
 namespace remoting {
@@ -31,11 +29,9 @@
                           const base::Closure& done) override;
 
  private:
-  void OnVideoAck(scoped_ptr<VideoAck> ack);
+  void OnIncomingMessage(scoped_ptr<CompoundBuffer> message) override;
 
-  ProtobufMessageParser<VideoAck> parser_;
-
-  VideoFeedbackStub* video_feedback_stub_;
+  VideoFeedbackStub* video_feedback_stub_ = nullptr;
 
   DISALLOW_COPY_AND_ASSIGN(HostVideoDispatcher);
 };
diff --git a/remoting/protocol/ice_connection_to_host.h b/remoting/protocol/ice_connection_to_host.h
index 717106c3..2fcdbdd 100644
--- a/remoting/protocol/ice_connection_to_host.h
+++ b/remoting/protocol/ice_connection_to_host.h
@@ -20,7 +20,6 @@
 #include "remoting/protocol/errors.h"
 #include "remoting/protocol/ice_transport.h"
 #include "remoting/protocol/input_filter.h"
-#include "remoting/protocol/message_reader.h"
 #include "remoting/protocol/monitored_video_stub.h"
 #include "remoting/protocol/session.h"
 #include "remoting/protocol/session_config.h"
diff --git a/remoting/protocol/message_reader.cc b/remoting/protocol/message_reader.cc
index 44389d71..3516595e 100644
--- a/remoting/protocol/message_reader.cc
+++ b/remoting/protocol/message_reader.cc
@@ -26,20 +26,18 @@
 MessageReader::MessageReader() : weak_factory_(this) {}
 MessageReader::~MessageReader() {}
 
-void MessageReader::SetMessageReceivedCallback(
-    const MessageReceivedCallback& callback) {
-  DCHECK(CalledOnValidThread());
-  message_received_callback_ = callback;
-}
-
 void MessageReader::StartReading(
     P2PStreamSocket* socket,
+    const MessageReceivedCallback& message_received_callback,
     const ReadFailedCallback& read_failed_callback) {
   DCHECK(CalledOnValidThread());
+  DCHECK(!socket_);
   DCHECK(socket);
+  DCHECK(!message_received_callback.is_null());
   DCHECK(!read_failed_callback.is_null());
 
   socket_ = socket;
+  message_received_callback_ = message_received_callback;
   read_failed_callback_ = read_failed_callback;
   DoRead();
 }
diff --git a/remoting/protocol/message_reader.h b/remoting/protocol/message_reader.h
index 39940736..4467e68 100644
--- a/remoting/protocol/message_reader.h
+++ b/remoting/protocol/message_reader.h
@@ -42,11 +42,9 @@
   MessageReader();
   virtual ~MessageReader();
 
-  // Sets the callback to be called for each incoming message.
-  void SetMessageReceivedCallback(const MessageReceivedCallback& callback);
-
   // Starts reading from |socket|.
   void StartReading(P2PStreamSocket* socket,
+                    const MessageReceivedCallback& message_received_callback,
                     const ReadFailedCallback& read_failed_callback);
 
  private:
diff --git a/remoting/protocol/message_reader_unittest.cc b/remoting/protocol/message_reader_unittest.cc
index 2361cb6..874fd71 100644
--- a/remoting/protocol/message_reader_unittest.cc
+++ b/remoting/protocol/message_reader_unittest.cc
@@ -53,10 +53,10 @@
   void TearDown() override { STLDeleteElements(&messages_); }
 
   void InitReader() {
-    reader_->SetMessageReceivedCallback(
-        base::Bind(&MessageReaderTest::OnMessage, base::Unretained(this)));
-    reader_->StartReading(&socket_, base::Bind(&MessageReaderTest::OnReadError,
-                                               base::Unretained(this)));
+    reader_->StartReading(
+        &socket_,
+        base::Bind(&MessageReaderTest::OnMessage, base::Unretained(this)),
+        base::Bind(&MessageReaderTest::OnReadError, base::Unretained(this)));
   }
 
   void AddMessage(const std::string& message) {
diff --git a/remoting/protocol/message_serialization.h b/remoting/protocol/message_serialization.h
index c550fbe..2a035ff5 100644
--- a/remoting/protocol/message_serialization.h
+++ b/remoting/protocol/message_serialization.h
@@ -9,6 +9,7 @@
 #define REMOTING_PROTOCOL_MESSAGE_SERIALIZATION_H_
 
 #include "net/base/io_buffer.h"
+#include "remoting/base/compound_buffer.h"
 
 #if defined(USE_SYSTEM_PROTOBUF)
 #include <google/protobuf/message_lite.h>
@@ -19,6 +20,18 @@
 namespace remoting {
 namespace protocol {
 
+template <class T>
+scoped_ptr<T> ParseMessage(CompoundBuffer* buffer) {
+  scoped_ptr<T> message(new T());
+  CompoundBufferInputStream stream(buffer);
+  if (!message->ParseFromZeroCopyStream(&stream)) {
+    LOG(WARNING) << "Received message that is not a valid protocol buffer.";
+    return nullptr;
+  }
+  DCHECK_EQ(stream.position(), buffer->total_bytes());
+  return message;
+}
+
 // Serialize the Protocol Buffer message and provide sufficient framing for
 // sending it over the wire.
 // This will provide sufficient prefix and suffix for the receiver side to
diff --git a/remoting/protocol/protobuf_message_parser.h b/remoting/protocol/protobuf_message_parser.h
deleted file mode 100644
index 43f86f060..0000000
--- a/remoting/protocol/protobuf_message_parser.h
+++ /dev/null
@@ -1,62 +0,0 @@
-// Copyright 2014 The Chromium 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 REMOTING_PROTOCOL_PROTOBUF_MESSAGE_PARSER_H_
-#define REMOTING_PROTOCOL_PROTOBUF_MESSAGE_PARSER_H_
-
-#include <utility>
-
-#include "base/bind.h"
-#include "base/callback.h"
-#include "base/memory/scoped_ptr.h"
-#include "remoting/base/compound_buffer.h"
-#include "remoting/protocol/message_reader.h"
-
-namespace remoting {
-namespace protocol {
-
-// Version of MessageReader for protocol buffer messages, that parses
-// each incoming message.
-template <class T>
-class ProtobufMessageParser {
- public:
-  // The callback that is called when a new message is received. |done_task|
-  // must be called by the callback when it's done processing the |message|.
-  typedef typename base::Callback<void(scoped_ptr<T> message)>
-      MessageReceivedCallback;
-
-  // |message_reader| must outlive ProtobufMessageParser.
-  ProtobufMessageParser(const MessageReceivedCallback& callback,
-                        MessageReader* message_reader)
-      : message_reader_(message_reader),
-        message_received_callback_(callback) {
-    message_reader->SetMessageReceivedCallback(base::Bind(
-        &ProtobufMessageParser<T>::OnNewData, base::Unretained(this)));
-  }
-  ~ProtobufMessageParser() {
-    message_reader_->SetMessageReceivedCallback(
-        MessageReader::MessageReceivedCallback());
-  }
-
- private:
-  void OnNewData(scoped_ptr<CompoundBuffer> buffer) {
-    scoped_ptr<T> message(new T());
-    CompoundBufferInputStream stream(buffer.get());
-    bool ret = message->ParseFromZeroCopyStream(&stream);
-    if (!ret) {
-      LOG(WARNING) << "Received message that is not a valid protocol buffer.";
-    } else {
-      DCHECK_EQ(stream.position(), buffer->total_bytes());
-      message_received_callback_.Run(std::move(message));
-    }
-  }
-
-  MessageReader* message_reader_;
-  MessageReceivedCallback message_received_callback_;
-};
-
-}  // namespace protocol
-}  // namespace remoting
-
-#endif  // REMOTING_PROTOCOL_PROTOBUF_MESSAGE_PARSER_H_
diff --git a/rlz/BUILD.gn b/rlz/BUILD.gn
index fd5862d..4bc22247 100644
--- a/rlz/BUILD.gn
+++ b/rlz/BUILD.gn
@@ -113,7 +113,6 @@
     ":rlz_lib",
     ":test_support",
     "//base",
-    "//base:prefs",
     "//net:test_support",
     "//testing/gmock",
     "//testing/gtest",
diff --git a/rlz/rlz.gyp b/rlz/rlz.gyp
index bd0fe23..e893eef 100644
--- a/rlz/rlz.gyp
+++ b/rlz/rlz.gyp
@@ -130,7 +130,6 @@
         ':rlz_lib',
         ':test_support_rlz',
         '../base/base.gyp:base',
-        '../base/base.gyp:base_prefs',
         '../testing/gmock.gyp:gmock',
         '../testing/gtest.gyp:gtest',
         '../third_party/zlib/zlib.gyp:zlib',
diff --git a/testing/buildbot/chromium.gpu.json b/testing/buildbot/chromium.gpu.json
index 9358097..a49ed05 100644
--- a/testing/buildbot/chromium.gpu.json
+++ b/testing/buildbot/chromium.gpu.json
@@ -298,31 +298,6 @@
           "--show-stdout",
           "--browser=debug",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Linux"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -648,31 +623,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Linux"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -983,31 +933,6 @@
           "--show-stdout",
           "--browser=debug",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "8086:0a2e",
-              "os": "Mac-10.10"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -1333,31 +1258,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "8086:0a2e",
-              "os": "Mac-10.10"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -1681,32 +1581,6 @@
           "--show-stdout",
           "--browser=debug",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "1002:6821",
-              "hidpi": "1",
-              "os": "Mac-10.10"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -2047,32 +1921,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "1002:6821",
-              "hidpi": "1",
-              "os": "Mac-10.10"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -2397,32 +2245,6 @@
           "--show-stdout",
           "--browser=debug",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:0fe9",
-              "hidpi": "1",
-              "os": "Mac"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -2763,32 +2585,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:0fe9",
-              "hidpi": "1",
-              "os": "Mac"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -3100,77 +2896,6 @@
           "--show-stdout",
           "--browser=debug",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=d3d9\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_d3d9_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=gl\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_gl_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=debug",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -3496,77 +3221,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "1002:6779",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=d3d9\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_d3d9_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "1002:6779",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=gl\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_gl_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "1002:6779",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
@@ -3892,77 +3546,6 @@
           "--show-stdout",
           "--browser=release",
           "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\"",
-          "--webgl-conformance-version=2.0.0",
-          "--webgl2-only=true"
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl2_conformance_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=d3d9\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_d3d9_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
-          "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc --use-angle=gl\""
-        ],
-        "isolate_name": "telemetry_gpu_test",
-        "name": "webgl_conformance_gl_tests",
-        "override_compile_targets": [
-          "telemetry_gpu_test_run"
-        ],
-        "swarming": {
-          "can_use_on_swarming_builders": true,
-          "dimension_sets": [
-            {
-              "gpu": "10de:104a",
-              "os": "Windows-2008ServerR2-SP1"
-            }
-          ]
-        }
-      },
-      {
-        "args": [
-          "webgl_conformance",
-          "--show-stdout",
-          "--browser=release",
-          "-v",
           "--extra-browser-args=\"--enable-logging=stderr --js-flags=--expose-gc\""
         ],
         "isolate_name": "telemetry_gpu_test",
diff --git a/testing/buildbot/chromium.memory.json b/testing/buildbot/chromium.memory.json
index 414709a..eab8e6a0 100644
--- a/testing/buildbot/chromium.memory.json
+++ b/testing/buildbot/chromium.memory.json
@@ -698,6 +698,12 @@
         "swarming": {
           "can_use_on_swarming_builders": true
         },
+        "test": "webkit_unit_tests"
+      },
+      {
+        "swarming": {
+          "can_use_on_swarming_builders": true
+        },
         "test": "wtf_unittests"
       }
     ]
diff --git a/testing/libfuzzer/fuzzers/BUILD.gn b/testing/libfuzzer/fuzzers/BUILD.gn
index d821c42..3976ad74 100644
--- a/testing/libfuzzer/fuzzers/BUILD.gn
+++ b/testing/libfuzzer/fuzzers/BUILD.gn
@@ -271,6 +271,7 @@
   deps = [
     "//third_party/libxml:libxml",
   ]
+  dict = "dicts/xml.dict"
 }
 
 fuzzer_test("unicode_string_codepage_create_fuzzer") {
diff --git a/testing/libfuzzer/fuzzers/dicts/xml.dict b/testing/libfuzzer/fuzzers/dicts/xml.dict
new file mode 100644
index 0000000..ff44a298
--- /dev/null
+++ b/testing/libfuzzer/fuzzers/dicts/xml.dict
@@ -0,0 +1,88 @@
+#
+# AFL dictionary for XML
+# ----------------------
+#
+# Several basic syntax elements and attributes, modeled on libxml2.
+#
+# Created by Michal Zalewski <lcamtuf@google.com>
+#
+
+attr_encoding=" encoding=\"1\""
+attr_generic=" a=\"1\""
+attr_href=" href=\"1\""
+attr_standalone=" standalone=\"no\""
+attr_version=" version=\"1\""
+attr_xml_base=" xml:base=\"1\""
+attr_xml_id=" xml:id=\"1\""
+attr_xml_lang=" xml:lang=\"1\""
+attr_xml_space=" xml:space=\"1\""
+attr_xmlns=" xmlns=\"1\""
+
+entity_builtin="&lt;"
+entity_decimal="&#1;"
+entity_external="&a;"
+entity_hex="&#x1;"
+
+string_any="ANY"
+string_brackets="[]"
+string_cdata="CDATA"
+string_col_fallback=":fallback"
+string_col_generic=":a"
+string_col_include=":include"
+string_dashes="--"
+string_empty="EMPTY"
+string_empty_dblquotes="\"\""
+string_empty_quotes="''"
+string_entities="ENTITIES"
+string_entity="ENTITY"
+string_fixed="#FIXED"
+string_id="ID"
+string_idref="IDREF"
+string_idrefs="IDREFS"
+string_implied="#IMPLIED"
+string_nmtoken="NMTOKEN"
+string_nmtokens="NMTOKENS"
+string_notation="NOTATION"
+string_parentheses="()"
+string_pcdata="#PCDATA"
+string_percent="%a"
+string_public="PUBLIC"
+string_required="#REQUIRED"
+string_schema=":schema"
+string_system="SYSTEM"
+string_ucs4="UCS-4"
+string_utf16="UTF-16"
+string_utf8="UTF-8"
+string_xmlns="xmlns:"
+
+tag_attlist="<!ATTLIST"
+tag_cdata="<![CDATA["
+tag_close="</a>"
+tag_doctype="<!DOCTYPE"
+tag_element="<!ELEMENT"
+tag_entity="<!ENTITY"
+tag_ignore="<![IGNORE["
+tag_include="<![INCLUDE["
+tag_notation="<!NOTATION"
+tag_open="<a>"
+tag_open_close="<a />"
+tag_open_exclamation="<!"
+tag_open_q="<?"
+tag_sq2_close="]]>"
+tag_xml_q="<?xml?>"
+"http://docboo"
+"http://www.w"
+"UTF-16LE"
+"xmlns"
+"he30"
+"he2"
+"IET"
+"FDF-10"
+"aDUCS-4OPveb:"
+"a>"
+"UT"
+"xMl"
+"/usr/share/sg"
+"ha07"
+"http://www.oa"
+"cle"
diff --git a/third_party/WebKit/LayoutTests/TestExpectations b/third_party/WebKit/LayoutTests/TestExpectations
index d3498ab..97d254d8 100644
--- a/third_party/WebKit/LayoutTests/TestExpectations
+++ b/third_party/WebKit/LayoutTests/TestExpectations
@@ -414,45 +414,45 @@
 crbug.com/563667 virtual/spv2/fast/block/basic/001.html [ Pass ]
 crbug.com/563667 virtual/spv2/fast/block/positioning/static-distance-with-positioned-ancestor.html [ Pass ]
 crbug.com/563667 virtual/spv2/fast/block/float/clamped-right-float.html [ Pass ]
-crbug.com/580355 fast/block/basic/018.html [ Pass ]
-crbug.com/580355 fast/block/basic/adding-near-anonymous-block.html [ Pass ]
-crbug.com/580355 fast/block/basic/text-indent-rtl.html [ Pass ]
-crbug.com/580355 fast/block/basic/truncation-rtl.html [ Pass ]
-crbug.com/580355 fast/block/basic/white-space-pre-wraps.html [ Pass ]
-crbug.com/580355 fast/block/float/001.html [ Pass ]
-crbug.com/580355 fast/block/float/002.html [ Pass ]
-crbug.com/580355 fast/block/float/float-in-float-hit-testing.html [ Pass ]
-crbug.com/580355 fast/block/float/independent-align-positioning.html [ Pass ]
-crbug.com/580355 fast/block/float/intruding-painted-twice.html [ Pass ]
-crbug.com/580355 fast/block/float/nopaint-after-layer-destruction.html [ Pass ]
-crbug.com/580355 fast/block/float/nopaint-after-layer-destruction2.html [ Pass ]
-crbug.com/580355 fast/block/float/shrink-to-fit-width.html [ Pass ]
-crbug.com/580355 fast/block/float/table-relayout.html [ Pass ]
-crbug.com/580355 fast/block/float/vertical-move-relayout.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/001.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/005.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/010.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/011.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/012.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/015.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/016.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/017.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/019.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/020.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/056.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/059.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/001.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/005.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/010.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/011.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/012.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/015.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/016.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/017.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/019.html [ Pass ]
-crbug.com/580355 fast/block/margin-collapse/block-inside-inline/020.html [ Pass ]
-crbug.com/580355 fast/block/positioning/height-change.html [ Pass ]
-crbug.com/580355 fast/block/positioning/relayout-on-position-change.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/basic/018.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/basic/adding-near-anonymous-block.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/basic/text-indent-rtl.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/basic/truncation-rtl.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/basic/white-space-pre-wraps.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/001.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/002.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/float-in-float-hit-testing.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/independent-align-positioning.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/intruding-painted-twice.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/nopaint-after-layer-destruction.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/nopaint-after-layer-destruction2.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/shrink-to-fit-width.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/table-relayout.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/float/vertical-move-relayout.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/001.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/005.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/010.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/011.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/012.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/015.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/016.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/017.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/019.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/020.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/056.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/059.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/001.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/005.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/010.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/011.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/012.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/015.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/016.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/017.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/019.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/margin-collapse/block-inside-inline/020.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/positioning/height-change.html [ Pass ]
+crbug.com/580355 virtual/spv2/fast/block/positioning/relayout-on-position-change.html [ Pass ]
 
 # In imported/web-platform-tests/html/, we prefer checking in failure
 # expectation files. The following tests with [ Failure ] don't have failure
diff --git a/third_party/WebKit/Source/bindings/core/v8/ScriptState.cpp b/third_party/WebKit/Source/bindings/core/v8/ScriptState.cpp
index 1f80618..d29d151 100644
--- a/third_party/WebKit/Source/bindings/core/v8/ScriptState.cpp
+++ b/third_party/WebKit/Source/bindings/core/v8/ScriptState.cpp
@@ -63,24 +63,9 @@
 
 void ScriptState::disposePerContextData()
 {
-    Vector<Observer*> observers(m_observers);
-    for (auto& observer : observers)
-        observer->willDisposeScriptState(this);
     m_perContextData = nullptr;
 }
 
-void ScriptState::addObserver(Observer* observer)
-{
-    m_observers.append(observer);
-}
-
-void ScriptState::removeObserver(Observer* observer)
-{
-    size_t index = m_observers.find(observer);
-    if (index != kNotFound)
-        m_observers.remove(index);
-}
-
 bool ScriptState::evalEnabled() const
 {
     v8::HandleScope handleScope(m_isolate);
diff --git a/third_party/WebKit/Source/bindings/core/v8/ScriptState.h b/third_party/WebKit/Source/bindings/core/v8/ScriptState.h
index 045b3009..5b5c5a0 100644
--- a/third_party/WebKit/Source/bindings/core/v8/ScriptState.h
+++ b/third_party/WebKit/Source/bindings/core/v8/ScriptState.h
@@ -103,14 +103,6 @@
     V8PerContextData* perContextData() const { return m_perContextData.get(); }
     void disposePerContextData();
 
-    class Observer {
-    public:
-        virtual ~Observer() { }
-        virtual void willDisposeScriptState(ScriptState*) = 0;
-    };
-    void addObserver(Observer*);
-    void removeObserver(Observer*);
-
     bool evalEnabled() const;
     void setEvalEnabled(bool);
     ScriptValue getFromGlobalObject(const char* name);
@@ -136,7 +128,6 @@
 #if ENABLE(ASSERT)
     bool m_globalObjectDetached;
 #endif
-    Vector<Observer*> m_observers;
 };
 
 // ScriptStateProtectingContext keeps the context associated with the ScriptState alive.
diff --git a/third_party/WebKit/Source/core/core.gypi b/third_party/WebKit/Source/core/core.gypi
index bcd1fb3..765317c 100644
--- a/third_party/WebKit/Source/core/core.gypi
+++ b/third_party/WebKit/Source/core/core.gypi
@@ -1799,8 +1799,6 @@
             'inspector/PageRuntimeAgent.h',
             'inspector/PromiseTracker.cpp',
             'inspector/PromiseTracker.h',
-            'inspector/RemoteObjectId.cpp',
-            'inspector/RemoteObjectId.h',
             'inspector/ScriptArguments.cpp',
             'inspector/ScriptArguments.h',
             'inspector/ScriptAsyncCallStack.cpp',
@@ -1829,6 +1827,8 @@
             'inspector/v8/ScriptBreakpoint.h',
             'inspector/v8/SourceMap.cpp',
             'inspector/v8/SourceMap.h',
+            'inspector/v8/RemoteObjectId.cpp',
+            'inspector/v8/RemoteObjectId.h',
             'inspector/v8/V8AsyncCallTracker.cpp',
             'inspector/v8/V8AsyncCallTracker.h',
             'inspector/v8/V8DebuggerAgent.h',
diff --git a/third_party/WebKit/Source/core/html/shadow/SliderThumbElement.cpp b/third_party/WebKit/Source/core/html/shadow/SliderThumbElement.cpp
index 2def680..ebdd408 100644
--- a/third_party/WebKit/Source/core/html/shadow/SliderThumbElement.cpp
+++ b/third_party/WebKit/Source/core/html/shadow/SliderThumbElement.cpp
@@ -144,7 +144,7 @@
         position -= isLeftToRightDirection ? layoutBox()->marginLeft() : layoutBox()->marginRight();
         currentPosition = absoluteThumbOrigin.x() - absoluteSliderContentOrigin.x();
     }
-    position = std::max<LayoutUnit>(0, std::min(position, trackSize));
+    position = std::min(position, trackSize).clampNegativeToZero();
     const Decimal ratio = Decimal::fromDouble(static_cast<double>(position) / trackSize);
     const Decimal fraction = isVertical || !isLeftToRightDirection ? Decimal(1) - ratio : ratio;
     StepRange stepRange(input->createStepRange(RejectAny));
diff --git a/third_party/WebKit/Source/core/inspector/InspectorDOMAgent.cpp b/third_party/WebKit/Source/core/inspector/InspectorDOMAgent.cpp
index 29c56344..c8b3538 100644
--- a/third_party/WebKit/Source/core/inspector/InspectorDOMAgent.cpp
+++ b/third_party/WebKit/Source/core/inspector/InspectorDOMAgent.cpp
@@ -69,9 +69,9 @@
 #include "core/inspector/InspectorHighlight.h"
 #include "core/inspector/InspectorHistory.h"
 #include "core/inspector/InstrumentingAgents.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/layout/HitTestResult.h"
 #include "core/layout/LayoutView.h"
 #include "core/loader/DocumentLoader.h"
diff --git a/third_party/WebKit/Source/core/inspector/InspectorDOMDebuggerAgent.cpp b/third_party/WebKit/Source/core/inspector/InspectorDOMDebuggerAgent.cpp
index 32552e9..d231ceae 100644
--- a/third_party/WebKit/Source/core/inspector/InspectorDOMDebuggerAgent.cpp
+++ b/third_party/WebKit/Source/core/inspector/InspectorDOMDebuggerAgent.cpp
@@ -40,11 +40,11 @@
 #include "core/frame/LocalDOMWindow.h"
 #include "core/inspector/InspectorDOMAgent.h"
 #include "core/inspector/InstrumentingAgents.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/EventListenerInfo.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8DebuggerAgent.h"
 #include "platform/JSONValues.h"
 
diff --git a/third_party/WebKit/Source/core/inspector/InspectorHeapProfilerAgent.cpp b/third_party/WebKit/Source/core/inspector/InspectorHeapProfilerAgent.cpp
index 1a42f302..5edb6f7 100644
--- a/third_party/WebKit/Source/core/inspector/InspectorHeapProfilerAgent.cpp
+++ b/third_party/WebKit/Source/core/inspector/InspectorHeapProfilerAgent.cpp
@@ -33,9 +33,9 @@
 #include "bindings/core/v8/V8Binding.h"
 #include "core/dom/Document.h"
 #include "core/frame/LocalDOMWindow.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "platform/Timer.h"
 #include "wtf/CurrentTime.h"
 #include <v8-profiler.h>
diff --git a/third_party/WebKit/Source/core/inspector/InspectorRuntimeAgent.cpp b/third_party/WebKit/Source/core/inspector/InspectorRuntimeAgent.cpp
index f873b4a..1dcdfe86 100644
--- a/third_party/WebKit/Source/core/inspector/InspectorRuntimeAgent.cpp
+++ b/third_party/WebKit/Source/core/inspector/InspectorRuntimeAgent.cpp
@@ -32,9 +32,9 @@
 
 #include "bindings/core/v8/ScriptState.h"
 #include "core/inspector/MuteConsoleScope.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8Debugger.h"
 #include "core/inspector/v8/V8RuntimeAgent.h"
 #include "platform/JSONValues.h"
diff --git a/third_party/WebKit/Source/core/inspector/PromiseTracker.cpp b/third_party/WebKit/Source/core/inspector/PromiseTracker.cpp
index 9fbc416..01965bd 100644
--- a/third_party/WebKit/Source/core/inspector/PromiseTracker.cpp
+++ b/third_party/WebKit/Source/core/inspector/PromiseTracker.cpp
@@ -5,8 +5,6 @@
 #include "core/inspector/PromiseTracker.h"
 
 #include "bindings/core/v8/ScriptCallStackFactory.h"
-#include "bindings/core/v8/ScriptState.h"
-#include "bindings/core/v8/ScriptValue.h"
 #include "core/inspector/ScriptAsyncCallStack.h"
 #include "wtf/CurrentTime.h"
 #include "wtf/PassOwnPtr.h"
@@ -121,15 +119,14 @@
     return id;
 }
 
-void PromiseTracker::didReceiveV8PromiseEvent(ScriptState* scriptState, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status)
+void PromiseTracker::didReceiveV8PromiseEvent(v8::Local<v8::Context> context, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status)
 {
     ASSERT(isEnabled());
-    ASSERT(scriptState->contextIsValid());
+    ASSERT(!context.IsEmpty());
 
     bool isNewPromise = false;
     int id = promiseId(promise, &isNewPromise);
 
-    ScriptState::Scope scope(scriptState);
     InspectorFrontend::Debugger::EventType::Enum eventType = isNewPromise ? InspectorFrontend::Debugger::EventType::New : InspectorFrontend::Debugger::EventType::Update;
 
     PromiseDetails::Status::Enum promiseStatus;
@@ -147,7 +144,7 @@
     promiseDetails->setStatus(promiseStatus);
 
     if (!parentPromise.IsEmpty() && parentPromise->IsObject()) {
-        v8::Local<v8::Object> handle = parentPromise->ToObject(scriptState->isolate());
+        v8::Local<v8::Object> handle = parentPromise->ToObject(context->GetIsolate());
         bool parentIsNewPromise = false;
         int parentPromiseId = promiseId(handle, &parentIsNewPromise);
         promiseDetails->setParentId(parentPromiseId);
@@ -184,14 +181,10 @@
     m_listener->didUpdatePromise(eventType, promiseDetails.release());
 }
 
-ScriptValue PromiseTracker::promiseById(int promiseId)
+v8::Local<v8::Object> PromiseTracker::promiseById(int promiseId)
 {
     ASSERT(isEnabled());
-    v8::HandleScope scope(m_isolate);
-    v8::Local<v8::Object> value = m_idToPromise.Get(promiseId);
-    if (value.IsEmpty())
-        return ScriptValue();
-    return ScriptValue(ScriptState::from(value->CreationContext()) , value);
+    return m_idToPromise.Get(promiseId);
 }
 
 } // namespace blink
diff --git a/third_party/WebKit/Source/core/inspector/PromiseTracker.h b/third_party/WebKit/Source/core/inspector/PromiseTracker.h
index eb804e4..7374202 100644
--- a/third_party/WebKit/Source/core/inspector/PromiseTracker.h
+++ b/third_party/WebKit/Source/core/inspector/PromiseTracker.h
@@ -19,9 +19,6 @@
 
 namespace blink {
 
-class ScriptState;
-class ScriptValue;
-
 class PromiseTracker final {
     WTF_MAKE_NONCOPYABLE(PromiseTracker);
     USING_FAST_MALLOC(PromiseTracker);
@@ -42,8 +39,8 @@
     bool isEnabled() const { return m_isEnabled; }
     void setEnabled(bool enabled, bool captureStacks);
     void clear();
-    void didReceiveV8PromiseEvent(ScriptState*, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status);
-    ScriptValue promiseById(int promiseId);
+    void didReceiveV8PromiseEvent(v8::Local<v8::Context>, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status);
+    v8::Local<v8::Object> promiseById(int promiseId);
 
 private:
     PromiseTracker(Listener*, v8::Isolate*);
diff --git a/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp b/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
index cb0d5f91..a0b42ff 100644
--- a/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
+++ b/third_party/WebKit/Source/core/inspector/ThreadDebugger.cpp
@@ -25,9 +25,25 @@
     InspectorDOMDebuggerAgent::eventListenersInfoForTarget(m_isolate, value, result);
 }
 
-v8::MaybeLocal<v8::Value> ThreadDebugger::compileAndRunInternalScript(const String& script)
+v8::MaybeLocal<v8::Object> ThreadDebugger::instantiateObject(v8::Local<v8::Function> function)
 {
-    return V8ScriptRunner::compileAndRunInternalScript(v8String(m_isolate, script), m_isolate);
+    return V8ScriptRunner::instantiateObject(m_isolate, function);
+}
+
+v8::MaybeLocal<v8::Script> ThreadDebugger::compileScript(v8::Local<v8::Context> context, v8::Local<v8::String> script, const String& fileName)
+{
+    v8::Context::Scope scope(context);
+    return V8ScriptRunner::compileScript(script, fileName, "", TextPosition(), m_isolate);
+}
+
+v8::MaybeLocal<v8::Value> ThreadDebugger::runCompiledScript(v8::Local<v8::Context> context, v8::Local<v8::Script> script)
+{
+    return V8ScriptRunner::runCompiledScript(m_isolate, script, toExecutionContext(context));
+}
+
+v8::MaybeLocal<v8::Value> ThreadDebugger::compileAndRunInternalScript(v8::Local<v8::String> script)
+{
+    return V8ScriptRunner::compileAndRunInternalScript(script, m_isolate);
 }
 
 v8::MaybeLocal<v8::Value> ThreadDebugger::callFunction(v8::Local<v8::Function> function, v8::Local<v8::Context> context, v8::Local<v8::Value> receiver, int argc, v8::Local<v8::Value> info[])
diff --git a/third_party/WebKit/Source/core/inspector/ThreadDebugger.h b/third_party/WebKit/Source/core/inspector/ThreadDebugger.h
index 7338a77..821b398 100644
--- a/third_party/WebKit/Source/core/inspector/ThreadDebugger.h
+++ b/third_party/WebKit/Source/core/inspector/ThreadDebugger.h
@@ -24,7 +24,10 @@
 
     // V8DebuggerClient implementation.
     void eventListeners(v8::Local<v8::Value>, EventListenerInfoMap&) override;
-    v8::MaybeLocal<v8::Value> compileAndRunInternalScript(const String& script) override;
+    v8::MaybeLocal<v8::Object> instantiateObject(v8::Local<v8::Function>) override;
+    v8::MaybeLocal<v8::Script> compileScript(v8::Local<v8::Context>, v8::Local<v8::String>, const String& fileName) override;
+    v8::MaybeLocal<v8::Value> runCompiledScript(v8::Local<v8::Context>, v8::Local<v8::Script>) override;
+    v8::MaybeLocal<v8::Value> compileAndRunInternalScript(v8::Local<v8::String>) override;
     v8::MaybeLocal<v8::Value> callFunction(v8::Local<v8::Function>, v8::Local<v8::Context>, v8::Local<v8::Value> receiver, int argc, v8::Local<v8::Value> info[]) override;
     v8::MaybeLocal<v8::Value> callInternalFunction(v8::Local<v8::Function>, v8::Local<v8::Value> receiver, int argc, v8::Local<v8::Value> info[]) override;
 
diff --git a/third_party/WebKit/Source/core/inspector/WorkerInspectorController.cpp b/third_party/WebKit/Source/core/inspector/WorkerInspectorController.cpp
index e6aef81..2f5960bd 100644
--- a/third_party/WebKit/Source/core/inspector/WorkerInspectorController.cpp
+++ b/third_party/WebKit/Source/core/inspector/WorkerInspectorController.cpp
@@ -146,10 +146,8 @@
     m_agents.append(InspectorTimelineAgent::create());
 
     m_injectedScriptManager->injectedScriptHost()->init(
-        m_workerDebuggerAgent->v8DebuggerAgent(),
         nullptr,
         bind<>(&InspectorConsoleAgent::clearAllMessages, workerConsoleAgentPtr),
-        m_workerThreadDebugger->debugger(),
         adoptPtr(new WorkerInjectedScriptHostClient()));
 }
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/DEPS b/third_party/WebKit/Source/core/inspector/v8/DEPS
index 250c0e4..1ee7dbb2 100644
--- a/third_party/WebKit/Source/core/inspector/v8/DEPS
+++ b/third_party/WebKit/Source/core/inspector/v8/DEPS
@@ -3,19 +3,13 @@
     "+bindings/core/v8/ExceptionState.h",
     "+bindings/core/v8/ScriptCallStackFactory.h",
     "+bindings/core/v8/ScriptRegexp.h",
-    "+bindings/core/v8/ScriptState.h",
-    "+bindings/core/v8/ScriptValue.h",
-    "+bindings/core/v8/V8AbstractEventListener.h",
     "+bindings/core/v8/V8Binding.h",
     "+bindings/core/v8/V8DOMException.h",
     "+bindings/core/v8/V8DOMTokenList.h",
     "+bindings/core/v8/V8GlobalValueMap.h",
-    "+bindings/core/v8/V8HiddenValue.h",
     "+bindings/core/v8/V8HTMLAllCollection.h",
     "+bindings/core/v8/V8HTMLCollection.h",
     "+bindings/core/v8/V8Node.h",
     "+bindings/core/v8/V8NodeList.h",
-    "+bindings/core/v8/V8PerContextData.h",
     "+bindings/core/v8/V8RecursionScope.h",
-    "+bindings/core/v8/V8ScriptRunner.h",
 ]
diff --git a/third_party/WebKit/Source/core/inspector/v8/InjectedScript.cpp b/third_party/WebKit/Source/core/inspector/v8/InjectedScript.cpp
index ffb1b90..7ba0a7d 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InjectedScript.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/InjectedScript.cpp
@@ -32,9 +32,9 @@
 
 #include "bindings/core/v8/V8Binding.h"
 #include "core/inspector/InspectorTraceEvents.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8Debugger.h"
 #include "core/inspector/v8/V8DebuggerClient.h"
 #include "core/inspector/v8/V8FunctionCall.h"
diff --git a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.cpp b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.cpp
index b6ec98d..8104e41f 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.cpp
@@ -32,7 +32,7 @@
 
 #include "core/inspector/InspectorConsoleAgent.h"
 #include "core/inspector/v8/V8Debugger.h"
-#include "core/inspector/v8/V8DebuggerAgent.h"
+#include "core/inspector/v8/V8DebuggerAgentImpl.h"
 #include "platform/JSONValues.h"
 
 #include "wtf/RefPtr.h"
diff --git a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.h b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.h
index 2fb2ecf..1216a11 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.h
+++ b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptHost.h
@@ -30,7 +30,6 @@
 #ifndef InjectedScriptHost_h
 #define InjectedScriptHost_h
 
-#include "bindings/core/v8/ScriptState.h"
 #include "core/InspectorTypeBuilder.h"
 #include "core/inspector/v8/InjectedScriptHostClient.h"
 #include "wtf/Functional.h"
@@ -46,8 +45,8 @@
 class InjectedScriptHostClient;
 class InspectorConsoleAgent;
 class JSONValue;
-class V8DebuggerAgent;
-class V8Debugger;
+class V8DebuggerImpl;
+class V8DebuggerAgentImpl;
 
 class EventListenerInfo;
 
@@ -64,15 +63,19 @@
     using InspectCallback = Function<void(PassRefPtr<TypeBuilder::Runtime::RemoteObject>, PassRefPtr<JSONObject>)>;
     using ClearConsoleCallback = Function<void()>;
 
-    void init(V8DebuggerAgent* debuggerAgent, PassOwnPtr<InspectCallback> inspectCallback, PassOwnPtr<ClearConsoleCallback> clearConsoleCallback, V8Debugger* debugger, PassOwnPtr<InjectedScriptHostClient> injectedScriptHostClient)
+    void init(PassOwnPtr<InspectCallback> inspectCallback, PassOwnPtr<ClearConsoleCallback> clearConsoleCallback, PassOwnPtr<InjectedScriptHostClient> injectedScriptHostClient)
     {
-        m_debuggerAgent = debuggerAgent;
         m_inspectCallback = std::move(inspectCallback);
         m_clearConsoleCallback = std::move(clearConsoleCallback);
-        m_debugger = debugger;
         m_client = std::move(injectedScriptHostClient);
     }
 
+    void setDebugger(V8DebuggerAgentImpl* debuggerAgent, V8DebuggerImpl* debugger)
+    {
+        m_debuggerAgent = debuggerAgent;
+        m_debugger = debugger;
+    }
+
     void disconnect();
 
     class InspectableObject {
@@ -93,7 +96,7 @@
     void monitorFunction(const String& scriptId, int lineNumber, int columnNumber, const String& functionName);
     void unmonitorFunction(const String& scriptId, int lineNumber, int columnNumber);
 
-    V8Debugger& debugger() { return *m_debugger; }
+    V8DebuggerImpl& debugger() { return *m_debugger; }
     InjectedScriptHostClient* client() { return m_client.get(); }
 
     // FIXME: store this template in per isolate data
@@ -103,10 +106,10 @@
 private:
     InjectedScriptHost();
 
-    V8DebuggerAgent* m_debuggerAgent;
+    V8DebuggerAgentImpl* m_debuggerAgent;
     OwnPtr<InspectCallback> m_inspectCallback;
     OwnPtr<ClearConsoleCallback> m_clearConsoleCallback;
-    V8Debugger* m_debugger;
+    V8DebuggerImpl* m_debugger;
     Vector<OwnPtr<InspectableObject>> m_inspectedObjects;
     OwnPtr<InspectableObject> m_defaultInspectableObject;
     OwnPtr<InjectedScriptHostClient> m_client;
diff --git a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptManager.cpp b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptManager.cpp
index cb8f174..d87412c 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptManager.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptManager.cpp
@@ -31,10 +31,10 @@
 #include "core/inspector/v8/InjectedScriptManager.h"
 
 #include "bindings/core/v8/V8Binding.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
 #include "core/inspector/v8/InjectedScriptNative.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8Debugger.h"
 #include "core/inspector/v8/V8DebuggerClient.h"
 #include "core/inspector/v8/V8InjectedScriptHost.h"
@@ -148,7 +148,7 @@
     return resultPtr;
 }
 
-v8::Local<v8::Object> InjectedScriptManager::createInjectedScript(const String& scriptSource, v8::Local<v8::Context> context, int id, InjectedScriptNative* injectedScriptNative)
+v8::Local<v8::Object> InjectedScriptManager::createInjectedScript(const String& source, v8::Local<v8::Context> context, int id, InjectedScriptNative* injectedScriptNative)
 {
     v8::Isolate* isolate = context->GetIsolate();
     v8::Context::Scope scope(context);
@@ -159,11 +159,12 @@
         m_injectedScriptHost->setWrapperTemplate(wrapperTemplate, isolate);
     }
 
-    v8::Local<v8::Object> scriptHostWrapper = V8InjectedScriptHost::wrap(wrapperTemplate, context, m_injectedScriptHost);
+    v8::Local<v8::Object> scriptHostWrapper = V8InjectedScriptHost::wrap(m_client, wrapperTemplate, context, m_injectedScriptHost);
     if (scriptHostWrapper.IsEmpty())
         return v8::Local<v8::Object>();
 
     injectedScriptNative->setOnInjectedScriptHost(scriptHostWrapper);
+    v8::Local<v8::String> sourceValue = v8::String::NewFromUtf8(isolate, source.utf8().data(), v8::NewStringType::kNormal).ToLocalChecked();
 
     // Inject javascript into the context. The compiled script is supposed to evaluate into
     // a single anonymous function(it's anonymous to avoid cluttering the global object with
@@ -171,7 +172,7 @@
     // injected script id and explicit reference to the inspected global object. The function is expected
     // to create and configure InjectedScript instance that is going to be used by the inspector.
     v8::Local<v8::Value> value;
-    if (!m_client->compileAndRunInternalScript(scriptSource).ToLocal(&value))
+    if (!m_client->compileAndRunInternalScript(sourceValue).ToLocal(&value))
         return v8::Local<v8::Object>();
     ASSERT(value->IsFunction());
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptNative.cpp b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptNative.cpp
index f994a4b..795a2d1 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InjectedScriptNative.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/InjectedScriptNative.cpp
@@ -25,7 +25,7 @@
 {
     v8::HandleScope handleScope(m_isolate);
     v8::Local<v8::External> external = v8::External::New(m_isolate, this);
-    v8::Local<v8::Private> privateKey = v8::Private::ForApi(m_isolate, v8::String::NewFromUtf8(m_isolate, privateKeyName));
+    v8::Local<v8::Private> privateKey = v8::Private::ForApi(m_isolate, v8::String::NewFromUtf8(m_isolate, privateKeyName, v8::NewStringType::kInternalized).ToLocalChecked());
     injectedScriptHost->SetPrivate(m_isolate->GetCurrentContext(), privateKey, external);
 }
 
@@ -34,13 +34,11 @@
     v8::Isolate* isolate = injectedScriptObject->GetIsolate();
     v8::HandleScope handleScope(isolate);
     v8::Local<v8::Context> context = isolate->GetCurrentContext();
-    v8::Local<v8::Private> privateKey = v8::Private::ForApi(isolate, v8::String::NewFromUtf8(isolate, privateKeyName));
-    v8::Local<v8::Value> value;
-    RELEASE_ASSERT(injectedScriptObject->GetPrivate(context, privateKey).ToLocal(&value));
+    v8::Local<v8::Private> privateKey = v8::Private::ForApi(isolate, v8::String::NewFromUtf8(isolate, privateKeyName, v8::NewStringType::kInternalized).ToLocalChecked());
+    v8::Local<v8::Value> value = injectedScriptObject->GetPrivate(context, privateKey).ToLocalChecked();
+    ASSERT(value->IsExternal());
     v8::Local<v8::External> external = value.As<v8::External>();
-    void* ptr = external->Value();
-    ASSERT(ptr);
-    return static_cast<InjectedScriptNative*>(ptr);
+    return static_cast<InjectedScriptNative*>(external->Value());
 }
 
 int InjectedScriptNative::bind(v8::Local<v8::Value> value, const String& groupName)
diff --git a/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.cpp b/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.cpp
index 123fd8d..f2ce47d 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.cpp
@@ -3,8 +3,8 @@
 // found in the LICENSE file.
 
 #include "core/inspector/v8/InspectorWrapper.h"
+#include "core/inspector/v8/V8DebuggerClient.h"
 
-#include "bindings/core/v8/V8ScriptRunner.h"
 #include "wtf/RefPtr.h"
 
 #include <v8-debug.h>
@@ -33,19 +33,15 @@
     return functionTemplate;
 }
 
-v8::Local<v8::Object> InspectorWrapperBase::createWrapper(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context)
+v8::Local<v8::Object> InspectorWrapperBase::createWrapper(V8DebuggerClient* client, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context)
 {
     v8::Local<v8::Function> function;
     if (!constructorTemplate->GetFunction(context).ToLocal(&function))
         return v8::Local<v8::Object>();
 
-    // FIXME: don't depend on V8ScriptRunner
-    v8::Isolate* isolate = context->GetIsolate();
-    v8::MaybeLocal<v8::Object> maybeResult = V8ScriptRunner::instantiateObject(isolate, function);
     v8::Local<v8::Object> result;
-    if (!maybeResult.ToLocal(&result))
+    if (!client->instantiateObject(function).ToLocal(&result))
         return v8::Local<v8::Object>();
-
     return result;
 }
 
@@ -53,8 +49,11 @@
 {
     v8::Isolate* isolate = context->GetIsolate();
     ASSERT(context != v8::Debug::GetDebugContext(isolate));
-    v8::Local<v8::Value> value = V8HiddenValue::getHiddenValue(ScriptState::from(context), object, v8InternalizedString(isolate, name));
-    if (value.IsEmpty())
+
+    v8::Local<v8::Private> privateKey = v8::Private::ForApi(isolate, v8::String::NewFromUtf8(isolate, name, v8::NewStringType::kInternalized).ToLocalChecked());
+
+    v8::Local<v8::Value> value;
+    if (!object->GetPrivate(context, privateKey).ToLocal(&value))
         return nullptr;
     if (!value->IsExternal())
         return nullptr;
diff --git a/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.h b/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.h
index 985c743..29c841e 100644
--- a/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.h
+++ b/third_party/WebKit/Source/core/inspector/v8/InspectorWrapper.h
@@ -5,9 +5,6 @@
 #ifndef InspectorWrapper_h
 #define InspectorWrapper_h
 
-#include "bindings/core/v8/ScriptValue.h"
-#include "bindings/core/v8/V8HiddenValue.h"
-#include "platform/heap/Handle.h"
 #include "wtf/PassRefPtr.h"
 #include "wtf/RefPtr.h"
 #include "wtf/Vector.h"
@@ -15,6 +12,8 @@
 
 namespace blink {
 
+class V8DebuggerClient;
+
 class InspectorWrapperBase {
 public:
     struct V8MethodConfiguration {
@@ -30,39 +29,25 @@
     static v8::Local<v8::FunctionTemplate> createWrapperTemplate(v8::Isolate*, const char* className, const Vector<V8MethodConfiguration>& methods, const Vector<V8AttributeConfiguration>& attributes);
 
 protected:
-    static v8::Local<v8::Object> createWrapper(v8::Local<v8::FunctionTemplate>, v8::Local<v8::Context>);
+    static v8::Local<v8::Object> createWrapper(V8DebuggerClient*, v8::Local<v8::FunctionTemplate>, v8::Local<v8::Context>);
     static void* unwrap(v8::Local<v8::Context>, v8::Local<v8::Object>, const char* name);
 
     static v8::Local<v8::String> v8InternalizedString(v8::Isolate*, const char* name);
 };
 
-template<typename T, bool = IsGarbageCollectedType<T>::value>
-class InspectorWrapperTypeTrait {
-public:
-    using PassType = PassRefPtr<T>;
-    using Type = RefPtr<T>;
-};
-
-template<typename T>
-class InspectorWrapperTypeTrait<T, true> {
-public:
-    using PassType = PassRefPtr<T>;
-    using Type = RefPtr<T>;
-};
-
 template<class T, char* const hiddenPropertyName, char* const className>
 class InspectorWrapper final : public InspectorWrapperBase {
 public:
     class WeakCallbackData final {
     public:
-        WeakCallbackData(v8::Isolate* isolate, typename InspectorWrapperTypeTrait<T>::PassType impl, v8::Local<v8::Object> wrapper)
+        WeakCallbackData(v8::Isolate* isolate, PassRefPtr<T> impl, v8::Local<v8::Object> wrapper)
             : m_impl(impl)
             , m_persistent(isolate, wrapper)
         {
             m_persistent.SetWeak(this, &WeakCallbackData::weakCallback, v8::WeakCallbackType::kParameter);
         }
 
-        typename InspectorWrapperTypeTrait<T>::Type m_impl;
+        RefPtr<T> m_impl;
 
     private:
         static void weakCallback(const v8::WeakCallbackInfo<WeakCallbackData>& info)
@@ -78,16 +63,18 @@
         return InspectorWrapperBase::createWrapperTemplate(isolate, className, methods, attributes);
     }
 
-    static v8::Local<v8::Object> wrap(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, typename blink::InspectorWrapperTypeTrait<T>::PassType object)
+    static v8::Local<v8::Object> wrap(V8DebuggerClient* client, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, PassRefPtr<T> object)
     {
         v8::Context::Scope contextScope(context);
-        v8::Local<v8::Object> result = InspectorWrapperBase::createWrapper(constructorTemplate, context);
+        v8::Local<v8::Object> result = InspectorWrapperBase::createWrapper(client, constructorTemplate, context);
         if (result.IsEmpty())
             return v8::Local<v8::Object>();
-        typename blink::InspectorWrapperTypeTrait<T>::Type impl(object);
+        RefPtr<T> impl(object);
         v8::Isolate* isolate = context->GetIsolate();
         v8::Local<v8::External> objectReference = v8::External::New(isolate, new WeakCallbackData(isolate, impl, result));
-        V8HiddenValue::setHiddenValue(ScriptState::from(context), result, v8InternalizedString(isolate, hiddenPropertyName), objectReference);
+
+        v8::Local<v8::Private> privateKey = v8::Private::ForApi(isolate, v8::String::NewFromUtf8(isolate, hiddenPropertyName, v8::NewStringType::kInternalized).ToLocalChecked());
+        result->SetPrivate(context, privateKey, objectReference);
         return result;
     }
     static T* unwrap(v8::Local<v8::Context> context, v8::Local<v8::Object> object)
diff --git a/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.cpp b/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.cpp
index df0deb2..85d8f8d3 100644
--- a/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.cpp
@@ -31,13 +31,14 @@
 #include "core/inspector/v8/JavaScriptCallFrame.h"
 
 #include "bindings/core/v8/V8Binding.h"
-#include "bindings/core/v8/V8ScriptRunner.h"
+#include "core/inspector/v8/V8DebuggerClient.h"
 #include <v8-debug.h>
 
 namespace blink {
 
-JavaScriptCallFrame::JavaScriptCallFrame(v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame)
-    : m_isolate(debuggerContext->GetIsolate())
+JavaScriptCallFrame::JavaScriptCallFrame(V8DebuggerClient* client, v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame)
+    : m_client(client)
+    , m_isolate(debuggerContext->GetIsolate())
     , m_debuggerContext(m_isolate, debuggerContext)
     , m_callFrame(m_isolate, callFrame)
 {
@@ -56,7 +57,7 @@
         v8::Local<v8::Value> callerFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame)->Get(v8AtomicString(m_isolate, "caller"));
         if (callerFrame.IsEmpty() || !callerFrame->IsObject())
             return 0;
-        m_caller = JavaScriptCallFrame::create(debuggerContext, v8::Local<v8::Object>::Cast(callerFrame));
+        m_caller = JavaScriptCallFrame::create(m_client, debuggerContext, v8::Local<v8::Object>::Cast(callerFrame));
     }
     return m_caller.get();
 }
@@ -68,7 +69,7 @@
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, name)));
     v8::Local<v8::Value> result;
-    if (!V8ScriptRunner::callInternalFunction(func, callFrame, 0, 0, m_isolate).ToLocal(&result) || !result->IsInt32())
+    if (!m_client->callInternalFunction(func, callFrame, 0, nullptr).ToLocal(&result) || !result->IsInt32())
         return 0;
     return result.As<v8::Int32>()->Value();
 }
@@ -80,7 +81,7 @@
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, name)));
     v8::Local<v8::Value> result;
-    if (!V8ScriptRunner::callInternalFunction(func, callFrame, 0, 0, m_isolate).ToLocal(&result))
+    if (!m_client->callInternalFunction(func, callFrame, 0, nullptr).ToLocal(&result))
         return String();
     return toCoreStringWithUndefinedOrNullCheck(result);
 }
@@ -124,7 +125,7 @@
 {
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, "scopeChain")));
-    v8::Local<v8::Array> scopeChain = v8::Local<v8::Array>::Cast(V8ScriptRunner::callInternalFunction(func, callFrame, 0, 0, m_isolate).ToLocalChecked());
+    v8::Local<v8::Array> scopeChain = v8::Local<v8::Array>::Cast(m_client->callInternalFunction(func, callFrame, 0, nullptr).ToLocalChecked());
     v8::Local<v8::Array> result = v8::Array::New(m_isolate, scopeChain->Length());
     for (uint32_t i = 0; i < scopeChain->Length(); i++)
         result->Set(i, scopeChain->Get(i));
@@ -135,7 +136,7 @@
 {
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, "scopeType")));
-    v8::Local<v8::Array> scopeType = v8::Local<v8::Array>::Cast(V8ScriptRunner::callInternalFunction(func, callFrame, 0, 0, m_isolate).ToLocalChecked());
+    v8::Local<v8::Array> scopeType = v8::Local<v8::Array>::Cast(m_client->callInternalFunction(func, callFrame, 0, nullptr).ToLocalChecked());
     return scopeType->Get(scopeIndex)->Int32Value();
 }
 
@@ -143,7 +144,7 @@
 {
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, "scopeName")));
-    v8::Local<v8::Array> scopeType = v8::Local<v8::Array>::Cast(V8ScriptRunner::callInternalFunction(func, callFrame, 0, 0, m_isolate).ToLocalChecked());
+    v8::Local<v8::Array> scopeType = v8::Local<v8::Array>::Cast(m_client->callInternalFunction(func, callFrame, 0, nullptr).ToLocalChecked());
     return scopeType->Get(scopeIndex)->ToString();
 }
 
@@ -183,7 +184,7 @@
     v8::TryCatch tryCatch(m_isolate);
     v8::Local<v8::Object> wrappedResult = v8::Object::New(m_isolate);
     v8::Local<v8::Value> result;
-    if (V8ScriptRunner::callInternalFunction(evalFunction, callFrame, WTF_ARRAY_LENGTH(argv), argv, m_isolate).ToLocal(&result)) {
+    if (m_client->callInternalFunction(evalFunction, callFrame, WTF_ARRAY_LENGTH(argv), argv).ToLocal(&result)) {
         wrappedResult->Set(v8::String::NewFromUtf8(m_isolate, "result"), result);
         wrappedResult->Set(v8::String::NewFromUtf8(m_isolate, "exceptionDetails"), v8::Undefined(m_isolate));
     } else {
@@ -198,7 +199,7 @@
     v8::Local<v8::Object> callFrame = v8::Local<v8::Object>::New(m_isolate, m_callFrame);
     v8::Local<v8::Function> restartFunction = v8::Local<v8::Function>::Cast(callFrame->Get(v8AtomicString(m_isolate, "restart")));
     v8::Debug::SetLiveEditEnabled(m_isolate, true);
-    v8::MaybeLocal<v8::Value> result = V8ScriptRunner::callInternalFunction(restartFunction, callFrame, 0, 0, m_isolate);
+    v8::MaybeLocal<v8::Value> result = m_client->callInternalFunction(restartFunction, callFrame, 0, nullptr);
     v8::Debug::SetLiveEditEnabled(m_isolate, false);
     return result;
 }
@@ -212,7 +213,7 @@
         variableName,
         newValue
     };
-    return V8ScriptRunner::callInternalFunction(setVariableValueFunction, callFrame, WTF_ARRAY_LENGTH(argv), argv, m_isolate);
+    return m_client->callInternalFunction(setVariableValueFunction, callFrame, WTF_ARRAY_LENGTH(argv), argv);
 }
 
 v8::Local<v8::Object> JavaScriptCallFrame::createExceptionDetails(v8::Isolate* isolate, v8::Local<v8::Message> message)
diff --git a/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.h b/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.h
index 6a87276..d0613eb8 100644
--- a/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.h
+++ b/third_party/WebKit/Source/core/inspector/v8/JavaScriptCallFrame.h
@@ -32,18 +32,19 @@
 #define JavaScriptCallFrame_h
 
 
-#include "bindings/core/v8/ScriptState.h"
 #include "wtf/RefCounted.h"
 #include "wtf/text/WTFString.h"
 #include <v8.h>
 
 namespace blink {
 
+class V8DebuggerClient;
+
 class JavaScriptCallFrame : public RefCounted<JavaScriptCallFrame> {
 public:
-    static PassRefPtr<JavaScriptCallFrame> create(v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame)
+    static PassRefPtr<JavaScriptCallFrame> create(V8DebuggerClient* client, v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame)
     {
-        return adoptRef(new JavaScriptCallFrame(debuggerContext, callFrame));
+        return adoptRef(new JavaScriptCallFrame(client, debuggerContext, callFrame));
     }
     ~JavaScriptCallFrame();
 
@@ -75,12 +76,15 @@
     void setWrapperTemplate(v8::Local<v8::FunctionTemplate> wrapperTemplate, v8::Isolate* isolate) { m_wrapperTemplate.Reset(isolate, wrapperTemplate); }
     v8::Local<v8::FunctionTemplate> wrapperTemplate(v8::Isolate* isolate) { return v8::Local<v8::FunctionTemplate>::New(isolate, m_wrapperTemplate); }
 
+    V8DebuggerClient* client() { return m_client; }
+
 private:
-    JavaScriptCallFrame(v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame);
+    JavaScriptCallFrame(V8DebuggerClient*, v8::Local<v8::Context> debuggerContext, v8::Local<v8::Object> callFrame);
 
     int callV8FunctionReturnInt(const char* name) const;
     String callV8FunctionReturnString(const char* name) const;
 
+    V8DebuggerClient* m_client;
     v8::Isolate* m_isolate;
     RefPtr<JavaScriptCallFrame> m_caller;
     v8::Global<v8::Context> m_debuggerContext;
diff --git a/third_party/WebKit/Source/core/inspector/RemoteObjectId.cpp b/third_party/WebKit/Source/core/inspector/v8/RemoteObjectId.cpp
similarity index 97%
rename from third_party/WebKit/Source/core/inspector/RemoteObjectId.cpp
rename to third_party/WebKit/Source/core/inspector/v8/RemoteObjectId.cpp
index abb046c..9040807 100644
--- a/third_party/WebKit/Source/core/inspector/RemoteObjectId.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/RemoteObjectId.cpp
@@ -2,7 +2,7 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
-#include "core/inspector/RemoteObjectId.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 
 #include "platform/JSONParser.h"
 #include "platform/JSONValues.h"
diff --git a/third_party/WebKit/Source/core/inspector/RemoteObjectId.h b/third_party/WebKit/Source/core/inspector/v8/RemoteObjectId.h
similarity index 100%
rename from third_party/WebKit/Source/core/inspector/RemoteObjectId.h
rename to third_party/WebKit/Source/core/inspector/v8/RemoteObjectId.h
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.cpp b/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.cpp
index d2092195..1d415ea 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.cpp
@@ -4,7 +4,6 @@
 
 #include "core/inspector/v8/V8AsyncCallTracker.h"
 
-#include "bindings/core/v8/V8PerContextData.h"
 #include "platform/heap/Handle.h"
 #include "wtf/HashMap.h"
 #include "wtf/text/StringBuilder.h"
@@ -30,13 +29,14 @@
     return builder.toString();
 }
 
-V8AsyncCallTracker::V8AsyncCallTracker(V8DebuggerAgentImpl* debuggerAgent) : m_debuggerAgent(debuggerAgent)
+V8AsyncCallTracker::V8AsyncCallTracker(V8DebuggerAgentImpl* debuggerAgent)
+    : m_debuggerAgent(debuggerAgent)
 {
 }
 
 V8AsyncCallTracker::~V8AsyncCallTracker()
 {
-    ASSERT(m_contextAsyncOperationMap.isEmpty());
+    ASSERT(m_idToOperations.isEmpty());
 }
 
 void V8AsyncCallTracker::asyncCallTrackingStateChanged(bool)
@@ -45,65 +45,74 @@
 
 void V8AsyncCallTracker::resetAsyncOperations()
 {
-    for (auto& it : m_contextAsyncOperationMap) {
-        it.key->removeObserver(this);
-        completeOperations(it.value.get());
-    }
-    m_contextAsyncOperationMap.clear();
+    for (auto& it : m_idToOperations)
+        completeOperations(it.value->map);
+    m_idToOperations.clear();
 }
 
-void V8AsyncCallTracker::willDisposeScriptState(ScriptState* state)
+void V8AsyncCallTracker::contextDisposed(int contextId)
 {
-    completeOperations(m_contextAsyncOperationMap.get(state));
-    m_contextAsyncOperationMap.remove(state);
+    completeOperations(m_idToOperations.get(contextId)->map);
+    m_idToOperations.remove(contextId);
 }
 
-void V8AsyncCallTracker::didReceiveV8AsyncTaskEvent(ScriptState* state, const String& eventType, const String& eventName, int id)
+void V8AsyncCallTracker::didReceiveV8AsyncTaskEvent(v8::Local<v8::Context> context, const String& eventType, const String& eventName, int id)
 {
     ASSERT(m_debuggerAgent->trackingAsyncCalls());
     if (eventType == v8AsyncTaskEventEnqueue)
-        didEnqueueV8AsyncTask(state, eventName, id);
+        didEnqueueV8AsyncTask(context, eventName, id);
     else if (eventType == v8AsyncTaskEventWillHandle)
-        willHandleV8AsyncTask(state, eventName, id);
+        willHandleV8AsyncTask(context, eventName, id);
     else if (eventType == v8AsyncTaskEventDidHandle)
         m_debuggerAgent->traceAsyncCallbackCompleted();
     else
         ASSERT_NOT_REACHED();
 }
 
-void V8AsyncCallTracker::didEnqueueV8AsyncTask(ScriptState* state, const String& eventName, int id)
+void V8AsyncCallTracker::weakCallback(const v8::WeakCallbackInfo<Operations>& data)
 {
-    ASSERT(state);
+    data.GetParameter()->target->contextDisposed(data.GetParameter()->contextId);
+}
+
+void V8AsyncCallTracker::didEnqueueV8AsyncTask(v8::Local<v8::Context> context, const String& eventName, int id)
+{
+    ASSERT(!context.IsEmpty());
     ASSERT(m_debuggerAgent->trackingAsyncCalls());
     int operationId = m_debuggerAgent->traceAsyncOperationStarting(eventName);
     if (!operationId)
         return;
-    V8ContextAsyncOperations* contextCallChains = m_contextAsyncOperationMap.get(state);
-    if (!contextCallChains)
-        contextCallChains = m_contextAsyncOperationMap.set(state, adoptPtr(new V8ContextAsyncOperations())).storedValue->value.get();
-    contextCallChains->set(makeV8AsyncTaskUniqueId(eventName, id), operationId);
+    int contextId = V8Debugger::contextId(context);
+    Operations* operations = m_idToOperations.get(contextId);
+    if (!operations) {
+        OwnPtr<Operations> newOperations = adoptPtr(new Operations());
+        newOperations->contextId = contextId;
+        newOperations->target = this;
+        newOperations->context.Reset(context->GetIsolate(), context);
+        operations = m_idToOperations.set(contextId, newOperations.release()).storedValue->value.get();
+        operations->context.SetWeak(operations, V8AsyncCallTracker::weakCallback, v8::WeakCallbackType::kParameter);
+    }
+    operations->map.set(makeV8AsyncTaskUniqueId(eventName, id), operationId);
 }
 
-void V8AsyncCallTracker::willHandleV8AsyncTask(ScriptState* state, const String& eventName, int id)
+void V8AsyncCallTracker::willHandleV8AsyncTask(v8::Local<v8::Context> context, const String& eventName, int id)
 {
-    ASSERT(state);
+    ASSERT(!context.IsEmpty());
     ASSERT(m_debuggerAgent->trackingAsyncCalls());
-    if (V8ContextAsyncOperations* contextCallChains = m_contextAsyncOperationMap.get(state)) {
+    int contextId = V8Debugger::contextId(context);
+    if (Operations* operations = m_idToOperations.get(contextId)) {
         String taskId = makeV8AsyncTaskUniqueId(eventName, id);
-        int operationId = contextCallChains->get(taskId);
+        int operationId = operations->map.get(taskId);
         m_debuggerAgent->traceAsyncCallbackStarting(operationId);
         m_debuggerAgent->traceAsyncOperationCompleted(operationId);
-        contextCallChains->remove(taskId);
+        operations->map.remove(taskId);
     } else {
         m_debuggerAgent->traceAsyncCallbackStarting(V8DebuggerAgentImpl::unknownAsyncOperationId);
     }
 }
 
-void V8AsyncCallTracker::completeOperations(V8ContextAsyncOperations* contextCallChains)
+void V8AsyncCallTracker::completeOperations(const HashMap<String, int>& contextCallChains)
 {
-    if (!contextCallChains)
-        return;
-    for (auto& it : *contextCallChains)
+    for (auto& it : contextCallChains)
         m_debuggerAgent->traceAsyncOperationCompleted(it.value);
 }
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.h b/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.h
index 3effdfc1..06ac7a9 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.h
+++ b/third_party/WebKit/Source/core/inspector/v8/V8AsyncCallTracker.h
@@ -5,18 +5,16 @@
 #ifndef V8AsyncCallTracker_h
 #define V8AsyncCallTracker_h
 
-#include "bindings/core/v8/ScriptState.h"
 #include "core/inspector/v8/V8DebuggerAgentImpl.h"
-#include "platform/heap/Handle.h"
 #include "wtf/Forward.h"
 #include "wtf/HashMap.h"
 #include "wtf/Noncopyable.h"
 
+#include <v8.h>
+
 namespace blink {
 
-class ScriptState;
-
-class V8AsyncCallTracker final : public ScriptState::Observer {
+class V8AsyncCallTracker final {
     WTF_MAKE_NONCOPYABLE(V8AsyncCallTracker);
     USING_FAST_MALLOC(V8AsyncCallTracker);
 public:
@@ -30,21 +28,28 @@
     void asyncCallTrackingStateChanged(bool tracking);
     void resetAsyncOperations();
 
-    void didReceiveV8AsyncTaskEvent(ScriptState*, const String& eventType, const String& eventName, int id);
+    void didReceiveV8AsyncTaskEvent(v8::Local<v8::Context>, const String& eventType, const String& eventName, int id);
 
-    // ScriptState::Observer implementation:
-    void willDisposeScriptState(ScriptState*) override;
+    void contextDisposed(int contextId);
 
 private:
+    struct Operations {
+        HashMap<String, int> map;
+        int contextId;
+        V8AsyncCallTracker* target;
+        v8::Global<v8::Context> context;
+    };
+
+    static void weakCallback(const v8::WeakCallbackInfo<Operations>& data);
+
     explicit V8AsyncCallTracker(V8DebuggerAgentImpl*);
-    using V8ContextAsyncOperations = HashMap<String, int>;
 
-    void didEnqueueV8AsyncTask(ScriptState*, const String& eventName, int id);
-    void willHandleV8AsyncTask(ScriptState*, const String& eventName, int id);
-    void completeOperations(V8ContextAsyncOperations* contextCallChains);
+    void didEnqueueV8AsyncTask(v8::Local<v8::Context>, const String& eventName, int id);
+    void willHandleV8AsyncTask(v8::Local<v8::Context>, const String& eventName, int id);
+    void completeOperations(const HashMap<String, int>& contextCallChains);
 
-    HashMap<RefPtr<ScriptState>, OwnPtr<V8ContextAsyncOperations>> m_contextAsyncOperationMap;
     V8DebuggerAgentImpl* m_debuggerAgent;
+    HashMap<int, OwnPtr<Operations>> m_idToOperations;
 };
 
 } // namespace blink
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.cpp b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.cpp
index 4f90ebc2..57d601a 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.cpp
@@ -6,24 +6,24 @@
 
 #include "bindings/core/v8/ScriptCallStackFactory.h"
 #include "bindings/core/v8/ScriptRegexp.h"
-#include "bindings/core/v8/ScriptValue.h"
 #include "bindings/core/v8/V8Binding.h"
 #include "bindings/core/v8/V8RecursionScope.h"
-#include "bindings/core/v8/V8ScriptRunner.h"
 #include "core/dom/Microtask.h"
 #include "core/inspector/AsyncCallChain.h"
 #include "core/inspector/ContentSearchUtils.h"
 #include "core/inspector/InstrumentingAgents.h"
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/ScriptAsyncCallStack.h"
 #include "core/inspector/ScriptCallFrame.h"
 #include "core/inspector/ScriptCallStack.h"
 #include "core/inspector/v8/IgnoreExceptionsScope.h"
 #include "core/inspector/v8/InjectedScript.h"
+#include "core/inspector/v8/InjectedScriptHost.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
 #include "core/inspector/v8/JavaScriptCallFrame.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8AsyncCallTracker.h"
 #include "core/inspector/v8/V8Debugger.h"
+#include "core/inspector/v8/V8DebuggerClient.h"
 #include "core/inspector/v8/V8JavaScriptCallFrame.h"
 #include "platform/JSONValues.h"
 #include "platform/SharedBuffer.h"
@@ -148,7 +148,6 @@
     , m_state(nullptr)
     , m_frontend(nullptr)
     , m_isolate(debugger->isolate())
-    , m_pausedScriptState(nullptr)
     , m_breakReason(InspectorFrontend::Debugger::Reason::Other)
     , m_scheduledDebuggerStep(NoStep)
     , m_skipNextDebuggerStepOut(false)
@@ -172,6 +171,8 @@
     , m_compiledScripts(debugger->isolate())
 {
     ASSERT(contextGroupId);
+    m_injectedScriptManager->injectedScriptHost()->setDebugger(this, m_debugger);
+
     // FIXME: remove once InjectedScriptManager moves to v8.
     m_v8AsyncCallTracker = V8AsyncCallTracker::create(this);
     m_promiseTracker = PromiseTracker::create(this, m_isolate);
@@ -229,7 +230,7 @@
     m_state->setBoolean(DebuggerAgentState::promiseTrackerCaptureStacks, false);
 
     debugger().removeAgent(m_contextGroupId);
-    m_pausedScriptState = nullptr;
+    m_pausedContext.Reset();
     m_currentCallStack.Reset();
     m_scripts.clear();
     m_sourceMaps.clear();
@@ -806,8 +807,7 @@
 void V8DebuggerAgentImpl::didReceiveV8AsyncTaskEvent(v8::Local<v8::Context> context, const String& eventType, const String& eventName, int id)
 {
     ASSERT(trackingAsyncCalls());
-    ScriptState* state = ScriptState::from(context);
-    m_v8AsyncCallTracker->didReceiveV8AsyncTaskEvent(state, eventType, eventName, id);
+    m_v8AsyncCallTracker->didReceiveV8AsyncTaskEvent(context, eventType, eventName, id);
 }
 
 bool V8DebuggerAgentImpl::v8PromiseEventsEnabled() const
@@ -818,8 +818,7 @@
 void V8DebuggerAgentImpl::didReceiveV8PromiseEvent(v8::Local<v8::Context> context, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status)
 {
     ASSERT(m_promiseTracker->isEnabled());
-    ScriptState* scriptState = ScriptState::from(context);
-    m_promiseTracker->didReceiveV8PromiseEvent(scriptState, promise, parentPromise, status);
+    m_promiseTracker->didReceiveV8PromiseEvent(context, promise, parentPromise, status);
 }
 
 void V8DebuggerAgentImpl::pause(ErrorString* errorString)
@@ -986,10 +985,10 @@
 
     v8::HandleScope handles(injectedScript->isolate());
     v8::Context::Scope scope(injectedScript->context());
-    v8::Local<v8::String> source = v8String(m_isolate, expression);
     v8::TryCatch tryCatch(m_isolate);
+    v8::Local<v8::String> expressionValue = v8::String::NewFromUtf8(m_isolate, expression.utf8().data(), v8::NewStringType::kNormal).ToLocalChecked();
     v8::Local<v8::Script> script;
-    if (!v8Call(V8ScriptRunner::compileScript(source, sourceURL, String(), TextPosition(), m_isolate), script, tryCatch)) {
+    if (!m_debugger->client()->compileScript(injectedScript->context(), expressionValue, sourceURL).ToLocal(&script)) {
         v8::Local<v8::Message> message = tryCatch.Message();
         if (!message.IsEmpty())
             exceptionDetails = createExceptionDetails(m_isolate, message);
@@ -1026,21 +1025,24 @@
     }
 
     v8::HandleScope handles(m_isolate);
-    v8::Context::Scope scope(injectedScript->context());
+    v8::Local<v8::Context> context = injectedScript->context();
+    v8::Context::Scope scope(context);
     v8::Local<v8::Script> script = v8::Local<v8::Script>::New(m_isolate, m_compiledScripts.Remove(scriptId));
-    ScriptState* scriptState = ScriptState::from(injectedScript->context());
 
-    if (script.IsEmpty() || !scriptState) {
+    if (script.IsEmpty()) {
         *errorString = "Script execution failed";
         return;
     }
     v8::TryCatch tryCatch(m_isolate);
     v8::Local<v8::Value> value;
-    if (!v8Call(V8ScriptRunner::runCompiledScript(m_isolate, script, scriptState->executionContext()), value, tryCatch)) {
+    v8::MaybeLocal<v8::Value> maybeValue = m_debugger->client()->runCompiledScript(context, script);
+    if (maybeValue.IsEmpty()) {
         value = tryCatch.Exception();
         v8::Local<v8::Message> message = tryCatch.Message();
         if (!message.IsEmpty())
             exceptionDetails = createExceptionDetails(m_isolate, message);
+    } else {
+        value = maybeValue.ToLocalChecked();
     }
 
     if (value.IsEmpty()) {
@@ -1146,14 +1148,14 @@
         *errorString = "Promise tracking is disabled";
         return;
     }
-    ScriptValue value = m_promiseTracker->promiseById(promiseId);
-    if (value.isEmpty()) {
+    v8::HandleScope handles(m_isolate);
+    v8::Local<v8::Object> value = m_promiseTracker->promiseById(promiseId);
+    if (value.IsEmpty()) {
         *errorString = "Promise with specified ID not found.";
         return;
     }
-    ScriptState::Scope scope(value.scriptState());
-    InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(value.context());
-    promise = injectedScript->wrapObject(value.v8Value(), objectGroup ? *objectGroup : "");
+    InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(value->CreationContext());
+    promise = injectedScript->wrapObject(value, objectGroup ? *objectGroup : "");
 }
 
 void V8DebuggerAgentImpl::didUpdatePromise(InspectorFrontend::Debugger::EventType::Enum eventType, PassRefPtr<TypeBuilder::Debugger::PromiseDetails> promise)
@@ -1194,7 +1196,7 @@
         m_pausingAsyncOperations.add(m_lastAsyncOperationId);
     }
 
-    if (m_pausedScriptState)
+    if (!m_pausedContext.IsEmpty())
         flushAsyncOperationEvents(nullptr);
     return m_lastAsyncOperationId;
 }
@@ -1431,12 +1433,12 @@
 
 PassRefPtr<Array<CallFrame>> V8DebuggerAgentImpl::currentCallFrames()
 {
-    if (!m_pausedScriptState || m_currentCallStack.IsEmpty())
+    if (m_pausedContext.IsEmpty() || m_currentCallStack.IsEmpty())
         return Array<CallFrame>::create();
     v8::HandleScope handles(m_isolate);
-    InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(m_pausedScriptState->context());
+    InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(m_pausedContext.Get(m_isolate));
     if (!injectedScript) {
-        ASSERT_NOT_REACHED();
+        // Context has been reported as removed while on pause.
         return Array<CallFrame>::create();
     }
 
@@ -1446,7 +1448,7 @@
 
 PassRefPtr<StackTrace> V8DebuggerAgentImpl::currentAsyncStackTrace()
 {
-    if (!m_pausedScriptState || !trackingAsyncCalls())
+    if (m_pausedContext.IsEmpty() || !trackingAsyncCalls())
         return nullptr;
     const AsyncCallChain* chain = m_currentAsyncCallChain.get();
     if (!chain)
@@ -1459,8 +1461,7 @@
     for (AsyncCallStackVector::const_reverse_iterator it = callStacks.rbegin(); it != callStacks.rend(); ++it, --asyncOrdinal) {
         v8::HandleScope scope(m_isolate);
         v8::Local<v8::Object> callFrames = (*it)->callFrames(m_isolate);
-        ScriptState* scriptState =  ScriptState::from(callFrames->CreationContext());
-        InjectedScript* injectedScript = scriptState ? m_injectedScriptManager->injectedScriptFor(scriptState->context()) : nullptr;
+        InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(callFrames->CreationContext());
         if (!injectedScript) {
             result.clear();
             continue;
@@ -1561,10 +1562,6 @@
 
 V8DebuggerAgentImpl::SkipPauseRequest V8DebuggerAgentImpl::didPause(v8::Local<v8::Context> context, v8::Local<v8::Object> callFrames, v8::Local<v8::Value> exception, const Vector<String>& hitBreakpoints, bool isPromiseRejection)
 {
-    ScriptState* scriptState = ScriptState::from(context);
-    if (!scriptState->contextIsValid())
-        return RequestContinue;
-
     if (isMuteBreakpointInstalled())
         return RequestContinue;
 
@@ -1588,14 +1585,13 @@
     if (callFrames.IsEmpty())
         return RequestContinue;
 
-    ASSERT(scriptState);
-    ASSERT(!m_pausedScriptState);
-    m_pausedScriptState = scriptState;
+    ASSERT(m_pausedContext.IsEmpty());
+    m_pausedContext.Reset(m_isolate, context);
     m_currentCallStack.Reset(m_isolate, callFrames);
     v8::HandleScope handles(m_isolate);
 
     if (!exception.IsEmpty()) {
-        InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(scriptState->context());
+        InjectedScript* injectedScript = m_injectedScriptManager->injectedScriptFor(context);
         if (injectedScript) {
             m_breakReason = isPromiseRejection ? InspectorFrontend::Debugger::Reason::PromiseRejection : InspectorFrontend::Debugger::Reason::Exception;
             m_breakAuxData = injectedScript->wrapObject(exception, V8DebuggerAgentImpl::backtraceObjectGroup)->openAccessors();
@@ -1642,7 +1638,7 @@
 
 void V8DebuggerAgentImpl::didContinue()
 {
-    m_pausedScriptState = nullptr;
+    m_pausedContext.Reset();
     m_currentCallStack.Reset();
     clearBreakDetails();
     m_frontend->resumed();
@@ -1656,7 +1652,7 @@
 void V8DebuggerAgentImpl::breakProgram(InspectorFrontend::Debugger::Reason::Enum breakReason, PassRefPtr<JSONObject> data)
 {
     ASSERT(enabled());
-    if (m_skipAllPauses || m_pausedScriptState || isCallStackEmptyOrBlackboxed())
+    if (m_skipAllPauses || !m_pausedContext.IsEmpty() || isCallStackEmptyOrBlackboxed())
         return;
     m_breakReason = breakReason;
     m_breakAuxData = data;
@@ -1683,7 +1679,7 @@
 
 bool V8DebuggerAgentImpl::assertPaused(ErrorString* errorString)
 {
-    if (!m_pausedScriptState) {
+    if (m_pausedContext.IsEmpty()) {
         *errorString = "Can only perform operation while paused.";
         return false;
     }
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.h b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.h
index ef18207..11be83a 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.h
+++ b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerAgentImpl.h
@@ -5,8 +5,6 @@
 #ifndef V8DebuggerAgentImpl_h
 #define V8DebuggerAgentImpl_h
 
-#include "bindings/core/v8/ScriptState.h"
-#include "bindings/core/v8/ScriptValue.h"
 #include "core/CoreExport.h"
 #include "core/InspectorFrontend.h"
 #include "core/inspector/InspectorBaseAgent.h"
@@ -152,6 +150,8 @@
     bool v8PromiseEventsEnabled() const;
     void didReceiveV8PromiseEvent(v8::Local<v8::Context>, v8::Local<v8::Object> promise, v8::Local<v8::Value> parentPromise, int status);
 
+    v8::Isolate* isolate() { return m_isolate; }
+
 private:
     bool checkEnabled(ErrorString*);
     void enable();
@@ -208,7 +208,7 @@
     RefPtr<JSONObject> m_state;
     InspectorFrontend::Debugger* m_frontend;
     v8::Isolate* m_isolate;
-    RefPtr<ScriptState> m_pausedScriptState;
+    v8::Global<v8::Context> m_pausedContext;
     v8::Global<v8::Object> m_currentCallStack;
     ScriptsMap m_scripts;
     BreakpointIdToDebuggerBreakpointIdsMap m_breakpointIdToDebuggerBreakpointIds;
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerClient.h b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerClient.h
index 9b5ad436c..5e3517b 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerClient.h
+++ b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerClient.h
@@ -21,7 +21,10 @@
     virtual void eventListeners(v8::Local<v8::Value>, EventListenerInfoMap&) = 0;
     virtual bool callingContextCanAccessContext(v8::Local<v8::Context> calling, v8::Local<v8::Context> target) = 0;
 
-    virtual v8::MaybeLocal<v8::Value> compileAndRunInternalScript(const String& script) = 0;
+    virtual v8::MaybeLocal<v8::Object> instantiateObject(v8::Local<v8::Function>) = 0;
+    virtual v8::MaybeLocal<v8::Script> compileScript(v8::Local<v8::Context>, v8::Local<v8::String>, const String& fileName) = 0;
+    virtual v8::MaybeLocal<v8::Value> runCompiledScript(v8::Local<v8::Context>, v8::Local<v8::Script>) = 0;
+    virtual v8::MaybeLocal<v8::Value> compileAndRunInternalScript(v8::Local<v8::String>) = 0;
     virtual v8::MaybeLocal<v8::Value> callFunction(v8::Local<v8::Function>, v8::Local<v8::Context>, v8::Local<v8::Value> receiver, int argc, v8::Local<v8::Value> info[]) = 0;
     virtual v8::MaybeLocal<v8::Value> callInternalFunction(v8::Local<v8::Function>, v8::Local<v8::Value> receiver, int argc, v8::Local<v8::Value> info[]) = 0;
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerImpl.cpp b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerImpl.cpp
index 1f43a282..09314d1 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8DebuggerImpl.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8DebuggerImpl.cpp
@@ -31,7 +31,6 @@
 #include "core/inspector/v8/V8DebuggerImpl.h"
 
 #include "bindings/core/v8/V8Binding.h"
-#include "bindings/core/v8/V8ScriptRunner.h"
 #include "core/inspector/v8/JavaScriptCallFrame.h"
 #include "core/inspector/v8/ScriptBreakpoint.h"
 #include "core/inspector/v8/V8DebuggerAgentImpl.h"
@@ -59,7 +58,7 @@
     v8::Local<v8::Object> debuggerScript = m_debuggerScript.Get(m_isolate);
     v8::Local<v8::Function> function = v8::Local<v8::Function>::Cast(debuggerScript->Get(v8InternalizedString(functionName)));
     ASSERT(m_isolate->InContext());
-    return V8ScriptRunner::callInternalFunction(function, debuggerScript, argc, argv, m_isolate);
+    return m_client->callInternalFunction(function, debuggerScript, argc, argv);
 }
 
 PassOwnPtr<V8Debugger> V8Debugger::create(v8::Isolate* isolate, V8DebuggerClient* client)
@@ -191,7 +190,7 @@
     v8::Local<v8::Function> getScriptsFunction = v8::Local<v8::Function>::Cast(debuggerScript->Get(v8InternalizedString("getScripts")));
     v8::Local<v8::Value> argv[] = { v8::Integer::New(m_isolate, contextGroupId) };
     v8::Local<v8::Value> value;
-    if (!V8ScriptRunner::callInternalFunction(getScriptsFunction, debuggerScript, WTF_ARRAY_LENGTH(argv), argv, m_isolate).ToLocal(&value))
+    if (!m_client->callInternalFunction(getScriptsFunction, debuggerScript, WTF_ARRAY_LENGTH(argv), argv).ToLocal(&value))
         return;
     ASSERT(value->IsArray());
     v8::Local<v8::Array> scriptsArray = v8::Local<v8::Array>::Cast(value);
@@ -476,7 +475,7 @@
     ASSERT(!currentCallFrameV8.IsEmpty());
     if (!currentCallFrameV8->IsObject())
         return nullptr;
-    return JavaScriptCallFrame::create(debuggerContext(), v8::Local<v8::Object>::Cast(currentCallFrameV8));
+    return JavaScriptCallFrame::create(m_client, debuggerContext(), v8::Local<v8::Object>::Cast(currentCallFrameV8));
 }
 
 v8::Local<v8::Object> V8DebuggerImpl::currentCallFramesInner(ScopeInfoDetails scopeDetails)
@@ -496,7 +495,7 @@
     v8::Local<v8::FunctionTemplate> wrapperTemplate = v8::Local<v8::FunctionTemplate>::New(m_isolate, m_callFrameWrapperTemplate);
     v8::Local<v8::Context> context = m_pausedContext.IsEmpty() ? m_isolate->GetCurrentContext() : m_pausedContext;
     v8::Context::Scope scope(context);
-    v8::Local<v8::Object> wrapper = V8JavaScriptCallFrame::wrap(wrapperTemplate, context, currentCallFrame.release());
+    v8::Local<v8::Object> wrapper = V8JavaScriptCallFrame::wrap(m_client, wrapperTemplate, context, currentCallFrame.release());
     return wrapper;
 }
 
@@ -527,7 +526,7 @@
     ASSERT(!currentCallFrameV8.IsEmpty());
     if (!currentCallFrameV8->IsObject())
         return nullptr;
-    return JavaScriptCallFrame::create(debuggerContext(), v8::Local<v8::Object>::Cast(currentCallFrameV8));
+    return JavaScriptCallFrame::create(m_client, debuggerContext(), v8::Local<v8::Object>::Cast(currentCallFrameV8));
 }
 
 static V8DebuggerImpl* toV8DebuggerImpl(v8::Local<v8::Value> data)
@@ -605,7 +604,7 @@
 {
     v8::Local<v8::Value> getterValue = object->Get(v8InternalizedString(functionName));
     ASSERT(!getterValue.IsEmpty() && getterValue->IsFunction());
-    return V8ScriptRunner::callInternalFunction(v8::Local<v8::Function>::Cast(getterValue), object, 0, 0, m_isolate).ToLocalChecked();
+    return m_client->callInternalFunction(v8::Local<v8::Function>::Cast(getterValue), object, 0, 0).ToLocalChecked();
 }
 
 void V8DebuggerImpl::handleV8DebugEvent(const v8::Debug::EventDetails& eventDetails)
@@ -712,10 +711,10 @@
 
     v8::HandleScope scope(m_isolate);
     v8::Context::Scope contextScope(debuggerContext());
-    const WebData& debuggerScriptSourceResource = Platform::current()->loadResource("DebuggerScriptSource.js");
-    String source(debuggerScriptSourceResource.data(), debuggerScriptSourceResource.size());
+    const WebData& source = Platform::current()->loadResource("DebuggerScriptSource.js");
+    v8::Local<v8::String> scriptValue = v8::String::NewFromUtf8(m_isolate, source.data(), v8::NewStringType::kInternalized, source.size()).ToLocalChecked();
     v8::Local<v8::Value> value;
-    if (!m_client->compileAndRunInternalScript(source).ToLocal(&value))
+    if (!m_client->compileAndRunInternalScript(scriptValue).ToLocal(&value))
         return;
     ASSERT(value->IsObject());
     m_debuggerScript.Reset(m_isolate, value.As<v8::Object>());
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8FunctionCall.cpp b/third_party/WebKit/Source/core/inspector/v8/V8FunctionCall.cpp
index 1f168d9b..ca612b2 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8FunctionCall.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8FunctionCall.cpp
@@ -39,10 +39,7 @@
 
 static v8::Local<v8::String> v8String(v8::Isolate* isolate, const String& string)
 {
-    v8::Local<v8::String> result;
-    bool success = v8::String::NewFromUtf8(isolate, string.utf8().data(), v8::NewStringType::kNormal).ToLocal(&result);
-    ASSERT_UNUSED(success, success);
-    return result;
+    return v8::String::NewFromUtf8(isolate, string.utf8().data(), v8::NewStringType::kNormal).ToLocalChecked();
 }
 
 V8FunctionCall::V8FunctionCall(V8DebuggerClient* client, v8::Local<v8::Context> context, v8::Local<v8::Value> value, const String& name)
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.cpp b/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.cpp
index 7a52c3f82..6982d89 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.cpp
@@ -5,7 +5,6 @@
 #include "core/inspector/v8/V8InjectedScriptHost.h"
 
 #include "bindings/core/v8/ExceptionState.h"
-#include "bindings/core/v8/V8AbstractEventListener.h"
 #include "bindings/core/v8/V8Binding.h"
 #include "bindings/core/v8/V8DOMException.h"
 #include "bindings/core/v8/V8DOMTokenList.h"
@@ -13,7 +12,6 @@
 #include "bindings/core/v8/V8HTMLCollection.h"
 #include "bindings/core/v8/V8Node.h"
 #include "bindings/core/v8/V8NodeList.h"
-#include "bindings/core/v8/V8ScriptRunner.h"
 #include "core/inspector/v8/EventListenerInfo.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptHost.h"
@@ -261,10 +259,9 @@
     if (info.Length() < 2)
         return;
 
-    InjectedScriptHost* host = V8InjectedScriptHost::unwrap(info.GetIsolate()->GetCurrentContext(), info.Holder());
-    ScriptState* scriptState = ScriptState::current(info.GetIsolate());
-    ScriptState::Scope scope(scriptState);
-    host->inspectImpl(toJSONValue(scriptState->context(), info[0]), toJSONValue(scriptState->context(), info[1]));
+    v8::Local<v8::Context> context = info.GetIsolate()->GetCurrentContext();
+    InjectedScriptHost* host = V8InjectedScriptHost::unwrap(context, info.Holder());
+    host->inspectImpl(toJSONValue(context, info[0]), toJSONValue(context, info[1]));
 }
 
 void V8InjectedScriptHost::evalCallback(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -284,7 +281,8 @@
     ASSERT(isolate->InContext());
     v8::TryCatch tryCatch(isolate);
     v8::Local<v8::Value> result;
-    if (!v8Call(V8ScriptRunner::compileAndRunInternalScript(expression, info.GetIsolate()), result, tryCatch)) {
+    InjectedScriptHost* host = V8InjectedScriptHost::unwrap(isolate->GetCurrentContext(), info.Holder());
+    if (!host->debugger().client()->compileAndRunInternalScript(expression).ToLocal(&result)) {
         v8SetReturnValue(info, tryCatch.ReThrow());
         return;
     }
@@ -319,28 +317,31 @@
         return;
 
     v8::TryCatch tryCatch(isolate);
+    v8::Local<v8::Context> context = isolate->GetCurrentContext();
+    InjectedScriptHost* host = V8InjectedScriptHost::unwrap(context, info.Holder());
+
     v8::Local<v8::Script> script;
-    v8::Local<v8::Value> result;
-    if (!v8Call(V8ScriptRunner::compileScript(expression, String(), String(), TextPosition(), isolate), script, tryCatch)) {
+    if (!host->debugger().client()->compileScript(context, expression, String()).ToLocal(&script)) {
         setExceptionAsReturnValue(info, wrappedResult, tryCatch);
         return;
     }
 
     v8::Local<v8::Symbol> commandLineAPISymbolValue = commandLineAPISymbol(isolate);
-    v8::Local<v8::Object> global = isolate->GetCurrentContext()->Global();
+    v8::Local<v8::Object> global = context->Global();
     if (info.Length() >= 2 && info[1]->IsObject()) {
         v8::Local<v8::Object> commandLineAPI = info[1]->ToObject(isolate);
         global->Set(commandLineAPISymbolValue, commandLineAPI);
     }
 
-    if (!v8Call(V8ScriptRunner::runCompiledScript(isolate, script, currentExecutionContext(isolate)), result, tryCatch)) {
-        global->Delete(isolate->GetCurrentContext(), commandLineAPISymbolValue);
+    v8::MaybeLocal<v8::Value> result = host->debugger().client()->runCompiledScript(context, script);
+    if (result.IsEmpty()) {
+        global->Delete(context, commandLineAPISymbolValue);
         setExceptionAsReturnValue(info, wrappedResult, tryCatch);
         return;
     }
 
-    global->Delete(isolate->GetCurrentContext(), commandLineAPISymbolValue);
-    wrappedResult->Set(v8::String::NewFromUtf8(isolate, "result"), result);
+    global->Delete(context, commandLineAPISymbolValue);
+    wrappedResult->Set(v8::String::NewFromUtf8(isolate, "result"), result.ToLocalChecked());
     wrappedResult->Set(v8::String::NewFromUtf8(isolate, "exceptionDetails"), v8::Undefined(isolate));
     v8SetReturnValue(info, wrappedResult);
 }
@@ -356,8 +357,7 @@
     v8::Local<v8::Value> newValue = info[3];
 
     InjectedScriptHost* host = V8InjectedScriptHost::unwrap(info.GetIsolate()->GetCurrentContext(), info.Holder());
-    V8DebuggerImpl& debugger = static_cast<V8DebuggerImpl&>(host->debugger());
-    v8SetReturnValue(info, debugger.setFunctionVariableValue(functionValue, scopeIndex, variableName, newValue));
+    v8SetReturnValue(info, host->debugger().setFunctionVariableValue(functionValue, scopeIndex, variableName, newValue));
 }
 
 static bool getFunctionLocation(const v8::FunctionCallbackInfo<v8::Value>& info, String* scriptId, int* lineNumber, int* columnNumber)
@@ -584,9 +584,9 @@
     return InjectedScriptHostWrapper::createWrapperTemplate(isolate, methods, attributes);
 }
 
-v8::Local<v8::Object> V8InjectedScriptHost::wrap(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, PassRefPtr<InjectedScriptHost> host)
+v8::Local<v8::Object> V8InjectedScriptHost::wrap(V8DebuggerClient* client, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, PassRefPtr<InjectedScriptHost> host)
 {
-    return InjectedScriptHostWrapper::wrap(constructorTemplate, context, host);
+    return InjectedScriptHostWrapper::wrap(client, constructorTemplate, context, host);
 }
 
 InjectedScriptHost* V8InjectedScriptHost::unwrap(v8::Local<v8::Context> context, v8::Local<v8::Object> object)
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.h b/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.h
index 3467d746..d915c2c 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.h
+++ b/third_party/WebKit/Source/core/inspector/v8/V8InjectedScriptHost.h
@@ -12,10 +12,11 @@
 namespace blink {
 
 class InjectedScriptHost;
+class V8DebuggerClient;
 
 class V8InjectedScriptHost {
 public:
-    static v8::Local<v8::Object> wrap(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context>, PassRefPtr<InjectedScriptHost>);
+    static v8::Local<v8::Object> wrap(V8DebuggerClient*, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context>, PassRefPtr<InjectedScriptHost>);
     static InjectedScriptHost* unwrap(v8::Local<v8::Context>, v8::Local<v8::Object>);
     static v8::Local<v8::FunctionTemplate> createWrapperTemplate(v8::Isolate*);
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.cpp b/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.cpp
index 769cf7d..c6d6b5a 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.cpp
@@ -24,7 +24,7 @@
     v8::Local<v8::FunctionTemplate> wrapperTemplate = impl->wrapperTemplate(isolate);
     if (wrapperTemplate.IsEmpty())
         return;
-    info.GetReturnValue().Set(V8JavaScriptCallFrame::wrap(wrapperTemplate, isolate->GetCurrentContext(), caller));
+    info.GetReturnValue().Set(V8JavaScriptCallFrame::wrap(impl->client(), wrapperTemplate, isolate->GetCurrentContext(), caller));
 }
 
 void sourceIDAttributeGetterCallback(v8::Local<v8::Name>, const v8::PropertyCallbackInfo<v8::Value>& info)
@@ -185,11 +185,11 @@
     return JavaScriptCallFrameWrapper::createWrapperTemplate(isolate, methods, attributes);
 }
 
-v8::Local<v8::Object> V8JavaScriptCallFrame::wrap(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, PassRefPtr<JavaScriptCallFrame> frame)
+v8::Local<v8::Object> V8JavaScriptCallFrame::wrap(V8DebuggerClient* client, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context> context, PassRefPtr<JavaScriptCallFrame> frame)
 {
     // Store template for .caller callback
     frame->setWrapperTemplate(constructorTemplate, context->GetIsolate());
-    return JavaScriptCallFrameWrapper::wrap(constructorTemplate, context, frame);
+    return JavaScriptCallFrameWrapper::wrap(client, constructorTemplate, context, frame);
 }
 
 JavaScriptCallFrame* V8JavaScriptCallFrame::unwrap(v8::Local<v8::Context> context, v8::Local<v8::Object> object)
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.h b/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.h
index d7b4c2b0..b7efa34 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.h
+++ b/third_party/WebKit/Source/core/inspector/v8/V8JavaScriptCallFrame.h
@@ -12,12 +12,13 @@
 namespace blink {
 
 class JavaScriptCallFrame;
+class V8DebuggerClient;
 
 class V8JavaScriptCallFrame {
     STATIC_ONLY(V8JavaScriptCallFrame);
 public:
     static v8::Local<v8::FunctionTemplate> createWrapperTemplate(v8::Isolate*);
-    static v8::Local<v8::Object> wrap(v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context>, PassRefPtr<JavaScriptCallFrame>);
+    static v8::Local<v8::Object> wrap(V8DebuggerClient*, v8::Local<v8::FunctionTemplate> constructorTemplate, v8::Local<v8::Context>, PassRefPtr<JavaScriptCallFrame>);
     static JavaScriptCallFrame* unwrap(v8::Local<v8::Context>, v8::Local<v8::Object>);
 };
 
diff --git a/third_party/WebKit/Source/core/inspector/v8/V8RuntimeAgentImpl.cpp b/third_party/WebKit/Source/core/inspector/v8/V8RuntimeAgentImpl.cpp
index c8557cb..6be5c93d 100644
--- a/third_party/WebKit/Source/core/inspector/v8/V8RuntimeAgentImpl.cpp
+++ b/third_party/WebKit/Source/core/inspector/v8/V8RuntimeAgentImpl.cpp
@@ -30,10 +30,10 @@
 
 #include "core/inspector/v8/V8RuntimeAgentImpl.h"
 
-#include "core/inspector/RemoteObjectId.h"
 #include "core/inspector/v8/IgnoreExceptionsScope.h"
 #include "core/inspector/v8/InjectedScript.h"
 #include "core/inspector/v8/InjectedScriptManager.h"
+#include "core/inspector/v8/RemoteObjectId.h"
 #include "core/inspector/v8/V8Debugger.h"
 #include "core/inspector/v8/V8DebuggerImpl.h"
 #include "platform/JSONValues.h"
diff --git a/third_party/WebKit/Source/core/layout/ColumnBalancer.h b/third_party/WebKit/Source/core/layout/ColumnBalancer.h
index f78e191..65328dc 100644
--- a/third_party/WebKit/Source/core/layout/ColumnBalancer.h
+++ b/third_party/WebKit/Source/core/layout/ColumnBalancer.h
@@ -132,7 +132,11 @@
 
         // Return the column height that this content run would require, considering the implicit
         // breaks assumed so far.
-        LayoutUnit columnLogicalHeight(LayoutUnit startOffset) const { return ceilf((m_breakOffset - startOffset).toFloat() / float(m_assumedImplicitBreaks + 1)); }
+        LayoutUnit columnLogicalHeight(LayoutUnit startOffset) const
+        {
+            // TODO(leviw): This should probably be fromFloatCeil.
+            return LayoutUnit(ceilf((m_breakOffset - startOffset) / float(m_assumedImplicitBreaks + 1)));
+        }
 
     private:
         LayoutUnit m_breakOffset; // Flow thread offset where this run ends.
diff --git a/third_party/WebKit/Source/core/layout/FloatingObjects.cpp b/third_party/WebKit/Source/core/layout/FloatingObjects.cpp
index 3ec05abd4..5d4b638 100644
--- a/third_party/WebKit/Source/core/layout/FloatingObjects.cpp
+++ b/third_party/WebKit/Source/core/layout/FloatingObjects.cpp
@@ -207,14 +207,14 @@
         }
     }
 
-    LayoutUnit lowestFloatBottom = 0;
+    LayoutUnit lowestFloatBottom;
     const FloatingObjectSet& floatingObjectSet = set();
     FloatingObjectSetIterator end = floatingObjectSet.end();
     if (floatType == FloatingObject::FloatLeftRight) {
         FloatingObject* lowestFloatingObjectLeft = nullptr;
         FloatingObject* lowestFloatingObjectRight = nullptr;
-        LayoutUnit lowestFloatBottomLeft = 0;
-        LayoutUnit lowestFloatBottomRight = 0;
+        LayoutUnit lowestFloatBottomLeft;
+        LayoutUnit lowestFloatBottomRight;
         for (FloatingObjectSetIterator it = floatingObjectSet.begin(); it != end; ++it) {
             FloatingObject& floatingObject = *it->get();
             if (floatingObject.isPlaced()) {
diff --git a/third_party/WebKit/Source/core/layout/LayoutBlock.cpp b/third_party/WebKit/Source/core/layout/LayoutBlock.cpp
index 376b79f..5a6d943d 100644
--- a/third_party/WebKit/Source/core/layout/LayoutBlock.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutBlock.cpp
@@ -955,9 +955,9 @@
         LayoutRect clientRect(noOverflowRect());
         LayoutRect rectToApply;
         if (isHorizontalWritingMode())
-            rectToApply = LayoutRect(clientRect.x(), clientRect.y(), 1, std::max<LayoutUnit>(0, oldClientAfterEdge - clientRect.y()));
+            rectToApply = LayoutRect(clientRect.x(), clientRect.y(), LayoutUnit(1), (oldClientAfterEdge - clientRect.y()).clampNegativeToZero());
         else
-            rectToApply = LayoutRect(clientRect.x(), clientRect.y(), std::max<LayoutUnit>(0, oldClientAfterEdge - clientRect.x()), 1);
+            rectToApply = LayoutRect(clientRect.x(), clientRect.y(), (oldClientAfterEdge - clientRect.x()).clampNegativeToZero(), LayoutUnit(1));
         addLayoutOverflow(rectToApply);
         if (hasOverflowModel())
             m_overflow->setLayoutClientAfterEdge(oldClientAfterEdge);
@@ -2060,8 +2060,8 @@
     }
 
     // Always make sure these values are non-negative.
-    minLogicalWidth = std::max<LayoutUnit>(0, minLogicalWidth);
-    maxLogicalWidth = std::max<LayoutUnit>(0, maxLogicalWidth);
+    minLogicalWidth = minLogicalWidth.clampNegativeToZero();
+    maxLogicalWidth = maxLogicalWidth.clampNegativeToZero();
 
     maxLogicalWidth = std::max(floatLeftWidth + floatRightWidth, maxLogicalWidth);
 }
diff --git a/third_party/WebKit/Source/core/layout/LayoutBlock.h b/third_party/WebKit/Source/core/layout/LayoutBlock.h
index 10a6df4c..1692b5a8 100644
--- a/third_party/WebKit/Source/core/layout/LayoutBlock.h
+++ b/third_party/WebKit/Source/core/layout/LayoutBlock.h
@@ -250,7 +250,7 @@
 
     virtual void scrollbarsChanged(bool /*horizontalScrollbarChanged*/, bool /*verticalScrollbarChanged*/) { }
 
-    LayoutUnit availableLogicalWidthForContent() const { return max<LayoutUnit>(0, logicalRightOffsetForContent() - logicalLeftOffsetForContent()); }
+    LayoutUnit availableLogicalWidthForContent() const { return (logicalRightOffsetForContent() - logicalLeftOffsetForContent()).clampNegativeToZero(); }
     LayoutUnit logicalLeftOffsetForContent() const { return isHorizontalWritingMode() ? borderLeft() + paddingLeft() : borderTop() + paddingTop(); }
     LayoutUnit logicalRightOffsetForContent() const { return logicalLeftOffsetForContent() + availableLogicalWidth(); }
     LayoutUnit startOffsetForContent() const { return style()->isLeftToRightDirection() ? logicalLeftOffsetForContent() : logicalWidth() - logicalRightOffsetForContent(); }
diff --git a/third_party/WebKit/Source/core/layout/LayoutBlockFlow.cpp b/third_party/WebKit/Source/core/layout/LayoutBlockFlow.cpp
index def8c097..91d4e99 100644
--- a/third_party/WebKit/Source/core/layout/LayoutBlockFlow.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutBlockFlow.cpp
@@ -109,8 +109,8 @@
     void setAtAfterSideOfBlock(bool b) { m_atAfterSideOfBlock = b; }
     void clearMargin()
     {
-        m_positiveMargin = 0;
-        m_negativeMargin = 0;
+        m_positiveMargin = LayoutUnit();
+        m_negativeMargin = LayoutUnit();
     }
     void setHasMarginBeforeQuirk(bool b) { m_hasMarginBeforeQuirk = b; }
     void setHasMarginAfterQuirk(bool b) { m_hasMarginAfterQuirk = b; }
@@ -291,7 +291,7 @@
     // Multiple passes might be required for column based layout.
     // The number of passes could be as high as the number of columns.
     bool done = false;
-    LayoutUnit pageLogicalHeight = 0;
+    LayoutUnit pageLogicalHeight;
     while (!done)
         done = layoutBlockFlow(relayoutChildren, pageLogicalHeight, layoutScope);
 
@@ -360,8 +360,8 @@
     LayoutUnit previousHeight = logicalHeight();
     setLogicalHeight(beforeEdge);
 
-    m_paintInvalidationLogicalTop = 0;
-    m_paintInvalidationLogicalBottom = 0;
+    m_paintInvalidationLogicalTop = LayoutUnit();
+    m_paintInvalidationLogicalBottom = LayoutUnit();
     if (!firstChild() && !isAnonymousBlock())
         setChildrenInline(true);
 
@@ -745,7 +745,7 @@
         // line, and we don't want to move all that, since it has already been established that it
         // fits nicely where it is.
         LayoutUnit lineHeight = lineBox.lineBottomWithLeading() - lineBox.lineTopWithLeading();
-        LayoutUnit totalLogicalHeight = lineHeight + std::max<LayoutUnit>(0, lineLogicalOffset);
+        LayoutUnit totalLogicalHeight = lineHeight + lineLogicalOffset.clampNegativeToZero();
         // It's rather pointless to break before the block if the current line isn't going to
         // fit in the same column or page, so check that as well.
         if (totalLogicalHeight <= pageLogicalHeight)
@@ -933,7 +933,7 @@
         LayoutBlockFlow* blockFlow = toLayoutBlockFlow(prev);
         logicalTopOffset -= blockFlow->logicalTop();
         if (blockFlow->lowestFloatLogicalBottom() > logicalTopOffset)
-            addIntrudingFloats(blockFlow, 0, logicalTopOffset);
+            addIntrudingFloats(blockFlow, LayoutUnit(), logicalTopOffset);
     }
 
     if (childrenInline()) {
@@ -949,7 +949,7 @@
                 if (oldFloatingObject) {
                     LayoutUnit oldLogicalBottom = logicalBottomForFloat(*oldFloatingObject);
                     if (logicalWidthForFloat(floatingObject) != logicalWidthForFloat(*oldFloatingObject) || logicalLeftForFloat(floatingObject) != logicalLeftForFloat(*oldFloatingObject)) {
-                        changeLogicalTop = 0;
+                        changeLogicalTop = LayoutUnit();
                         changeLogicalBottom = std::max(changeLogicalBottom, std::max(logicalBottom, oldLogicalBottom));
                     } else {
                         if (logicalBottom != oldLogicalBottom) {
@@ -971,7 +971,7 @@
 
                     floatMap.remove(floatingObject.layoutObject());
                 } else {
-                    changeLogicalTop = 0;
+                    changeLogicalTop = LayoutUnit();
                     changeLogicalBottom = std::max(changeLogicalBottom, logicalBottom);
                 }
             }
@@ -981,7 +981,7 @@
         for (LayoutBoxToFloatInfoMap::iterator it = floatMap.begin(); it != end; ++it) {
             OwnPtr<FloatingObject>& floatingObject = it->value;
             if (!floatingObject->isDescendant()) {
-                changeLogicalTop = 0;
+                changeLogicalTop = LayoutUnit();
                 changeLogicalBottom = std::max(changeLogicalBottom, logicalBottomForFloat(*floatingObject));
             }
         }
@@ -1015,7 +1015,7 @@
     // It doesn't get included in the normal layout process but is instead skipped.
     LayoutObject* childToExclude = layoutSpecialExcludedChild(relayoutChildren, layoutScope);
 
-    LayoutUnit previousFloatLogicalBottom = 0;
+    LayoutUnit previousFloatLogicalBottom;
 
     LayoutBox* next = firstChildBox();
     LayoutBox* lastNormalFlowChild = nullptr;
@@ -1098,13 +1098,13 @@
 
 LayoutBlockFlow::MarginValues LayoutBlockFlow::marginValuesForChild(LayoutBox& child) const
 {
-    LayoutUnit childBeforePositive = 0;
-    LayoutUnit childBeforeNegative = 0;
-    LayoutUnit childAfterPositive = 0;
-    LayoutUnit childAfterNegative = 0;
+    LayoutUnit childBeforePositive;
+    LayoutUnit childBeforeNegative;
+    LayoutUnit childAfterPositive;
+    LayoutUnit childAfterNegative;
 
-    LayoutUnit beforeMargin = 0;
-    LayoutUnit afterMargin = 0;
+    LayoutUnit beforeMargin;
+    LayoutUnit afterMargin;
 
     LayoutBlockFlow* childLayoutBlockFlow = child.isLayoutBlockFlow() ? toLayoutBlockFlow(&child) : 0;
 
@@ -1426,8 +1426,8 @@
     // The margins are discarded by a child that specified -webkit-margin-collapse: discard.
     // FIXME: Use writing mode independent accessor for marginBeforeCollapse.
     if (child.style()->marginBeforeCollapse() == MDISCARD) {
-        positiveMarginBefore = 0;
-        negativeMarginBefore = 0;
+        positiveMarginBefore = LayoutUnit();
+        negativeMarginBefore = LayoutUnit();
         discardMarginBefore = true;
         return;
     }
@@ -1482,8 +1482,8 @@
     // relayout if there are intruding floats.
     LayoutUnit logicalTopEstimate = logicalHeight();
     if (!marginInfo.canCollapseWithMarginBefore()) {
-        LayoutUnit positiveMarginBefore = 0;
-        LayoutUnit negativeMarginBefore = 0;
+        LayoutUnit positiveMarginBefore;
+        LayoutUnit negativeMarginBefore;
         bool discardMarginBefore = false;
         if (child.selfNeedsLayout()) {
             // Try to do a basic estimation of how the collapse is going to go.
@@ -1830,7 +1830,7 @@
 
     // At least one float is present. We need to perform the clearance computation.
     bool clearSet = child->style()->clear() != CNONE;
-    LayoutUnit logicalBottom = 0;
+    LayoutUnit logicalBottom;
     switch (child->style()->clear()) {
     case CNONE:
         break;
@@ -1846,7 +1846,7 @@
     }
 
     // We also clear floats if we are too big to sit on the same line as a float (and wish to avoid floats by default).
-    LayoutUnit result = clearSet ? std::max<LayoutUnit>(0, logicalBottom - logicalTop) : LayoutUnit();
+    LayoutUnit result = clearSet ? (logicalBottom - logicalTop).clampNegativeToZero() : LayoutUnit();
     if (!result && child->avoidsFloats()) {
         LayoutUnit newLogicalTop = logicalTop;
         LayoutRect borderBox = child->borderBoxRect();
@@ -2094,8 +2094,8 @@
             invalidatePaintRectangle(reflectedRect(paintInvalidationRect));
     }
 
-    m_paintInvalidationLogicalTop = 0;
-    m_paintInvalidationLogicalBottom = 0;
+    m_paintInvalidationLogicalTop = LayoutUnit();
+    m_paintInvalidationLogicalBottom = LayoutUnit();
 }
 
 void LayoutBlockFlow::paintFloats(const PaintInfo& paintInfo, const LayoutPoint& paintOffset) const
@@ -2126,7 +2126,7 @@
 {
     positionNewFloats();
     // set y position
-    LayoutUnit newY = 0;
+    LayoutUnit newY;
     switch (clear) {
     case CLEFT:
         newY = lowestFloatLogicalBottom(FloatingObject::FloatLeft);
@@ -2221,8 +2221,8 @@
     bool insideFlowThread = flowThreadContainingBlock();
 
     if (childBox->style()->floating() == LeftFloat) {
-        LayoutUnit heightRemainingLeft = 1;
-        LayoutUnit heightRemainingRight = 1;
+        LayoutUnit heightRemainingLeft = LayoutUnit(1);
+        LayoutUnit heightRemainingRight = LayoutUnit(1);
         floatLogicalLeft = logicalLeftOffsetForPositioningFloat(logicalTopOffset, logicalLeftOffset, &heightRemainingLeft);
         while (logicalRightOffsetForPositioningFloat(logicalTopOffset, logicalRightOffset, &heightRemainingRight) - floatLogicalLeft < floatLogicalWidth) {
             logicalTopOffset += std::min<LayoutUnit>(heightRemainingLeft, heightRemainingRight);
@@ -2236,8 +2236,8 @@
         }
         floatLogicalLeft = std::max(logicalLeftOffset - borderAndPaddingLogicalLeft(), floatLogicalLeft);
     } else {
-        LayoutUnit heightRemainingLeft = 1;
-        LayoutUnit heightRemainingRight = 1;
+        LayoutUnit heightRemainingLeft = LayoutUnit(1);
+        LayoutUnit heightRemainingRight = LayoutUnit(1);
         floatLogicalLeft = logicalRightOffsetForPositioningFloat(logicalTopOffset, logicalRightOffset, &heightRemainingRight);
         while (floatLogicalLeft - logicalLeftOffsetForPositioningFloat(logicalTopOffset, logicalLeftOffset, &heightRemainingLeft) < floatLogicalWidth) {
             logicalTopOffset += std::min(heightRemainingLeft, heightRemainingRight);
@@ -2319,7 +2319,7 @@
                     floatingObject.setOriginatingLine(nullptr);
 #endif
                 }
-                markLinesDirtyInBlockRange(0, logicalBottom);
+                markLinesDirtyInBlockRange(LayoutUnit(), logicalBottom);
             }
             m_floatingObjects->remove(&floatingObject);
         }
@@ -2640,7 +2640,7 @@
 
 IntRect alignSelectionRectToDevicePixels(LayoutRect& rect)
 {
-    LayoutUnit roundedX = rect.x().round();
+    LayoutUnit roundedX = LayoutUnit(rect.x().round());
     return IntRect(roundedX, rect.y().round(),
         (rect.maxX() - roundedX).round(),
         snapSizeToPixel(rect.height(), rect.y()));
@@ -2843,7 +2843,7 @@
     }
 
     FrameView* frameView = document().view();
-    LayoutUnit top = (style()->position() == FixedPosition) ? 0 : frameView->scrollOffset().height();
+    LayoutUnit top = LayoutUnit((style()->position() == FixedPosition) ? 0 : frameView->scrollOffset().height());
     int visibleHeight = frameView->visibleContentRect(IncludeScrollbars).height();
     if (size().height() < visibleHeight)
         top += (visibleHeight - size().height()) / 2;
diff --git a/third_party/WebKit/Source/core/layout/LayoutBlockFlow.h b/third_party/WebKit/Source/core/layout/LayoutBlockFlow.h
index d2f34141..face324 100644
--- a/third_party/WebKit/Source/core/layout/LayoutBlockFlow.h
+++ b/third_party/WebKit/Source/core/layout/LayoutBlockFlow.h
@@ -101,7 +101,7 @@
 
     LayoutUnit availableLogicalWidthForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = LayoutUnit()) const
     {
-        return (logicalRightOffsetForLine(position, indentText, logicalHeight) - logicalLeftOffsetForLine(position, indentText, logicalHeight)).clampToZero();
+        return (logicalRightOffsetForLine(position, indentText, logicalHeight) - logicalLeftOffsetForLine(position, indentText, logicalHeight)).clampNegativeToZero();
     }
     LayoutUnit logicalRightOffsetForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = LayoutUnit()) const
     {
@@ -292,11 +292,11 @@
 
     void addOverflowFromFloats();
 
-    LayoutUnit logicalRightOffsetForLine(LayoutUnit logicalTop, LayoutUnit fixedOffset, IndentTextOrNot applyTextIndent, LayoutUnit logicalHeight = 0) const
+    LayoutUnit logicalRightOffsetForLine(LayoutUnit logicalTop, LayoutUnit fixedOffset, IndentTextOrNot applyTextIndent, LayoutUnit logicalHeight = LayoutUnit()) const
     {
         return adjustLogicalRightOffsetForLine(logicalRightFloatOffsetForLine(logicalTop, fixedOffset, logicalHeight), applyTextIndent);
     }
-    LayoutUnit logicalLeftOffsetForLine(LayoutUnit logicalTop, LayoutUnit fixedOffset, IndentTextOrNot applyTextIndent, LayoutUnit logicalHeight = 0) const
+    LayoutUnit logicalLeftOffsetForLine(LayoutUnit logicalTop, LayoutUnit fixedOffset, IndentTextOrNot applyTextIndent, LayoutUnit logicalHeight = LayoutUnit()) const
     {
         return adjustLogicalLeftOffsetForLine(logicalLeftFloatOffsetForLine(logicalTop, fixedOffset, logicalHeight), applyTextIndent);
     }
@@ -447,19 +447,19 @@
 
         static LayoutUnit positiveMarginBeforeDefault(const LayoutBlockFlow* block)
         {
-            return block->marginBefore().clampToZero();
+            return block->marginBefore().clampNegativeToZero();
         }
         static LayoutUnit negativeMarginBeforeDefault(const LayoutBlockFlow* block)
         {
-            return (-block->marginBefore()).clampToZero();
+            return (-block->marginBefore()).clampNegativeToZero();
         }
         static LayoutUnit positiveMarginAfterDefault(const LayoutBlockFlow* block)
         {
-            return block->marginAfter().clampToZero();
+            return block->marginAfter().clampNegativeToZero();
         }
         static LayoutUnit negativeMarginAfterDefault(const LayoutBlockFlow* block)
         {
-            return (-block->marginAfter()).clampToZero();
+            return (-block->marginAfter()).clampNegativeToZero();
         }
 
         MarginValues m_margins;
diff --git a/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp b/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp
index 50b2975..22d3119 100644
--- a/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp
@@ -570,9 +570,9 @@
         if (!style()->right().isAuto() && !containingBlock->style()->isLeftToRightDirection())
             offset.setWidth(-valueForLength(style()->right(), containingBlock->availableWidth()));
         else
-            offset.expand(valueForLength(style()->left(), containingBlock->availableWidth()), 0);
+            offset.expand(valueForLength(style()->left(), containingBlock->availableWidth()), LayoutUnit());
     } else if (!style()->right().isAuto()) {
-        offset.expand(-valueForLength(style()->right(), containingBlock->availableWidth()), 0);
+        offset.expand(-valueForLength(style()->right(), containingBlock->availableWidth()), LayoutUnit());
     }
 
     // If the containing block of a relatively positioned element does not
@@ -585,13 +585,13 @@
         && (!containingBlock->hasAutoHeightOrContainingBlockWithAutoHeight()
             || !style()->top().hasPercent()
             || containingBlock->stretchesToViewport()))
-        offset.expand(0, valueForLength(style()->top(), containingBlock->availableHeight()));
+        offset.expand(LayoutUnit(), valueForLength(style()->top(), containingBlock->availableHeight()));
 
     else if (!style()->bottom().isAuto()
         && (!containingBlock->hasAutoHeightOrContainingBlockWithAutoHeight()
             || !style()->bottom().hasPercent()
             || containingBlock->stretchesToViewport()))
-        offset.expand(0, -valueForLength(style()->bottom(), containingBlock->availableHeight()));
+        offset.expand(LayoutUnit(), -valueForLength(style()->bottom(), containingBlock->availableHeight()));
 
     return offset;
 }
@@ -669,7 +669,7 @@
 
 LayoutUnit LayoutBoxModelObject::computedCSSPadding(const Length& padding) const
 {
-    LayoutUnit w = 0;
+    LayoutUnit w;
     if (padding.hasPercent())
         w = containingBlockLogicalWidthForContent();
     return minimumValueForLength(padding, w);
@@ -677,12 +677,12 @@
 
 static inline LayoutUnit resolveWidthForRatio(LayoutUnit height, const FloatSize& intrinsicRatio)
 {
-    return height * intrinsicRatio.width() / intrinsicRatio.height();
+    return LayoutUnit(height * intrinsicRatio.width() / intrinsicRatio.height());
 }
 
 static inline LayoutUnit resolveHeightForRatio(LayoutUnit width, const FloatSize& intrinsicRatio)
 {
-    return width * intrinsicRatio.height() / intrinsicRatio.width();
+    return LayoutUnit(width * intrinsicRatio.height() / intrinsicRatio.width());
 }
 
 static inline LayoutSize resolveAgainstIntrinsicWidthOrHeightAndRatio(const LayoutSize& size, const FloatSize& intrinsicRatio, LayoutUnit useWidth, LayoutUnit useHeight)
@@ -913,7 +913,7 @@
             x -= textIndentOffset;
         break;
     }
-    x = std::min(x, (maxX - caretWidth()).clampToZero());
+    x = std::min(x, (maxX - caretWidth()).clampNegativeToZero());
 
     LayoutUnit height = LayoutUnit(style()->fontMetrics().height());
     LayoutUnit verticalSpace = lineHeight(true, currentStyle.isHorizontalWritingMode() ? HorizontalLine : VerticalLine,  PositionOfInteriorLineBoxes) - height;
diff --git a/third_party/WebKit/Source/core/layout/LayoutDeprecatedFlexibleBox.cpp b/third_party/WebKit/Source/core/layout/LayoutDeprecatedFlexibleBox.cpp
index ac3fa87..2b491cc 100644
--- a/third_party/WebKit/Source/core/layout/LayoutDeprecatedFlexibleBox.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutDeprecatedFlexibleBox.cpp
@@ -147,7 +147,7 @@
     // Fixed margins can be added in as is.
     Length marginLeft = child->style()->marginLeft();
     Length marginRight = child->style()->marginRight();
-    LayoutUnit margin = 0;
+    LayoutUnit margin;
     if (marginLeft.isFixed())
         margin += marginLeft.value();
     if (marginRight.isFixed())
@@ -211,7 +211,7 @@
 
     maxLogicalWidth = std::max(minLogicalWidth, maxLogicalWidth);
 
-    LayoutUnit scrollbarWidth = intrinsicScrollbarLogicalWidth();
+    LayoutUnit scrollbarWidth(intrinsicScrollbarLogicalWidth());
     maxLogicalWidth += scrollbarWidth;
     minLogicalWidth += scrollbarWidth;
 }
@@ -297,9 +297,9 @@
     LayoutUnit yPos = borderTop() + paddingTop();
     LayoutUnit xPos = borderLeft() + paddingLeft();
     bool heightSpecified = false;
-    LayoutUnit oldHeight = 0;
+    LayoutUnit oldHeight;
 
-    LayoutUnit remainingSpace = 0;
+    LayoutUnit remainingSpace;
 
 
     FlexBoxIterator iterator(this);
@@ -321,7 +321,8 @@
         // Our first pass is done without flexing.  We simply lay the children
         // out within the box.  We have to do a layout first in order to determine
         // our box's intrinsic height.
-        LayoutUnit maxAscent = 0, maxDescent = 0;
+        LayoutUnit maxAscent;
+        LayoutUnit maxDescent;
         for (LayoutBox* child = iterator.first(); child; child = iterator.next()) {
             if (child->isOutOfFlowPositioned())
                 continue;
@@ -343,7 +344,7 @@
 
             // Update our height and overflow height.
             if (style()->boxAlign() == BBASELINE) {
-                LayoutUnit ascent = child->firstLineBoxBaseline();
+                LayoutUnit ascent(child->firstLineBoxBaseline());
                 if (ascent == -1)
                     ascent = child->size().height() + child->marginBottom();
                 ascent += child->marginTop();
@@ -419,10 +420,10 @@
             LayoutUnit childY = yPos;
             switch (style()->boxAlign()) {
             case BCENTER:
-                childY += child->marginTop() + ((contentHeight() - (child->size().height() + child->marginHeight())) / 2).clampToZero();
+                childY += child->marginTop() + ((contentHeight() - (child->size().height() + child->marginHeight())) / 2).clampNegativeToZero();
                 break;
             case BBASELINE: {
-                LayoutUnit ascent = child->firstLineBoxBaseline();
+                LayoutUnit ascent(child->firstLineBoxBaseline());
                 if (ascent == -1)
                     ascent = child->size().height() + child->marginBottom();
                 ascent += child->marginTop();
@@ -484,7 +485,7 @@
                     // The flex groups may not have any flexible objects this time around.
                     if (!spaceAvailableThisPass || totalFlex == 0.0f) {
                         // If we just couldn't grow/shrink any more, then it's time to transition to the next flex group.
-                        groupRemainingSpace = 0;
+                        groupRemainingSpace = LayoutUnit();
                         continue;
                     }
 
@@ -510,7 +511,7 @@
                     }
                     if (groupRemainingSpace == groupRemainingSpaceAtBeginning) {
                         // This is not advancing, avoid getting stuck by distributing the remaining pixels.
-                        LayoutUnit spaceAdd = groupRemainingSpace > 0 ? 1 : -1;
+                        LayoutUnit spaceAdd = LayoutUnit(groupRemainingSpace > 0 ? 1 : -1);
                         for (LayoutBox* child = iterator.first(); child && groupRemainingSpace; child = iterator.next()) {
                             if (allowedChildFlex(child, expanding, i)) {
                                 child->setOverrideLogicalContentWidth(contentWidthForChild(child) + spaceAdd);
@@ -535,7 +536,7 @@
     if (remainingSpace > 0 && ((style()->isLeftToRightDirection() && style()->boxPack() != Start)
         || (!style()->isLeftToRightDirection() && style()->boxPack() != End))) {
         // Children must be repositioned.
-        LayoutUnit offset = 0;
+        LayoutUnit offset;
         if (style()->boxPack() == Justify) {
             // Determine the total number of children.
             int totalChildren = 0;
@@ -591,9 +592,9 @@
     LayoutUnit yPos = borderTop() + paddingTop();
     LayoutUnit toAdd = borderBottom() + paddingBottom() + horizontalScrollbarHeight();
     bool heightSpecified = false;
-    LayoutUnit oldHeight = 0;
+    LayoutUnit oldHeight;
 
-    LayoutUnit remainingSpace = 0;
+    LayoutUnit remainingSpace;
 
     FlexBoxIterator iterator(this);
     unsigned highestFlexGroup = 0;
@@ -658,7 +659,7 @@
             switch (style()->boxAlign()) {
             case BCENTER:
             case BBASELINE: // Baseline just maps to center for vertical boxes
-                childX += child->marginLeft() + std::max<LayoutUnit>(LayoutUnit(), (contentWidth() - (child->size().width() + child->marginWidth())) / 2);
+                childX += child->marginLeft() + ((contentWidth() - (child->size().width() + child->marginWidth())) / 2).clampNegativeToZero();
                 break;
             case BEND:
                 if (!style()->isLeftToRightDirection())
@@ -738,7 +739,7 @@
                     // The flex groups may not have any flexible objects this time around.
                     if (!spaceAvailableThisPass || totalFlex == 0.0f) {
                         // If we just couldn't grow/shrink any more, then it's time to transition to the next flex group.
-                        groupRemainingSpace = 0;
+                        groupRemainingSpace = LayoutUnit();
                         continue;
                     }
 
@@ -761,7 +762,7 @@
                     }
                     if (groupRemainingSpace == groupRemainingSpaceAtBeginning) {
                         // This is not advancing, avoid getting stuck by distributing the remaining pixels.
-                        LayoutUnit spaceAdd = groupRemainingSpace > 0 ? 1 : -1;
+                        LayoutUnit spaceAdd = LayoutUnit(groupRemainingSpace > 0 ? 1 : -1);
                         for (LayoutBox* child = iterator.first(); child && groupRemainingSpace; child = iterator.next()) {
                             if (allowedChildFlex(child, expanding, i)) {
                                 child->setOverrideLogicalContentHeight(contentHeightForChild(child) + spaceAdd);
@@ -785,7 +786,7 @@
 
     if (style()->boxPack() != Start && remainingSpace > 0) {
         // Children must be repositioned.
-        LayoutUnit offset = 0;
+        LayoutUnit offset;
         if (style()->boxPack() == Justify) {
             // Determine the total number of children.
             int totalChildren = 0;
@@ -876,7 +877,7 @@
         if (lineCount <= numVisibleLines)
             continue;
 
-        LayoutUnit newHeight = blockChild->heightForLineCount(numVisibleLines);
+        LayoutUnit newHeight(blockChild->heightForLineCount(numVisibleLines));
         if (newHeight == child->size().height())
             continue;
 
@@ -919,7 +920,7 @@
         // Let the truncation code kick in.
         // FIXME: the text alignment should be recomputed after the width changes due to truncation.
         LayoutUnit blockLeftEdge = destBlock.logicalLeftOffsetForLine(lastVisibleLine->y(), DoNotIndentText);
-        lastVisibleLine->placeEllipsis(ellipsisStr, leftToRight, blockLeftEdge, blockRightEdge, totalWidth);
+        lastVisibleLine->placeEllipsis(ellipsisStr, leftToRight, blockLeftEdge, blockRightEdge, LayoutUnit(totalWidth));
         destBlock.setHasMarkupTruncation(true);
     }
 }
@@ -956,7 +957,7 @@
 LayoutUnit LayoutDeprecatedFlexibleBox::allowedChildFlex(LayoutBox* child, bool expanding, unsigned group)
 {
     if (childDoesNotAffectWidthOrFlexing(child) || child->style()->boxFlex() == 0.0f || child->style()->boxFlexGroup() != group)
-        return 0;
+        return LayoutUnit();
 
     if (expanding) {
         if (isHorizontal()) {
@@ -964,19 +965,19 @@
             LayoutUnit maxWidth = LayoutUnit::max();
             LayoutUnit width = contentWidthForChild(child);
             if (child->style()->maxWidth().isFixed())
-                maxWidth = child->style()->maxWidth().value();
+                maxWidth = LayoutUnit(child->style()->maxWidth().value());
             if (maxWidth == LayoutUnit::max())
                 return maxWidth;
-            return std::max<LayoutUnit>(0, maxWidth - width);
+            return (maxWidth - width).clampNegativeToZero();
         }
         // FIXME: For now just handle fixed values.
         LayoutUnit maxHeight = LayoutUnit::max();
         LayoutUnit height = contentHeightForChild(child);
         if (child->style()->maxHeight().isFixed())
-            maxHeight = child->style()->maxHeight().value();
+            maxHeight = LayoutUnit(child->style()->maxHeight().value());
         if (maxHeight == LayoutUnit::max())
             return maxHeight;
-        return std::max<LayoutUnit>(0, maxHeight - height);
+        return (maxHeight - height).clampNegativeToZero();
     }
 
     // FIXME: For now just handle fixed values.
@@ -984,21 +985,21 @@
         LayoutUnit minWidth = child->minPreferredLogicalWidth();
         LayoutUnit width = contentWidthForChild(child);
         if (child->style()->minWidth().isFixed())
-            minWidth = child->style()->minWidth().value();
+            minWidth = LayoutUnit(child->style()->minWidth().value());
         else if (child->style()->minWidth().type() == Auto)
-            minWidth = 0;
+            minWidth = LayoutUnit();
 
-        LayoutUnit allowedShrinkage = std::min<LayoutUnit>(0, minWidth - width);
+        LayoutUnit allowedShrinkage = (minWidth - width).clampPositiveToZero();
         return allowedShrinkage;
     }
     Length minHeight = child->style()->minHeight();
     if (minHeight.isFixed() || minHeight.isAuto()) {
-        LayoutUnit minHeight = child->style()->minHeight().value();
+        LayoutUnit minHeight(child->style()->minHeight().value());
         LayoutUnit height = contentHeightForChild(child);
-        LayoutUnit allowedShrinkage = std::min<LayoutUnit>(0, minHeight - height);
+        LayoutUnit allowedShrinkage = (minHeight - height).clampPositiveToZero();
         return allowedShrinkage;
     }
-    return 0;
+    return LayoutUnit();
 }
 
 } // namespace blink
diff --git a/third_party/WebKit/Source/core/layout/LayoutFieldset.cpp b/third_party/WebKit/Source/core/layout/LayoutFieldset.cpp
index fa14c3f7..1af7515 100644
--- a/third_party/WebKit/Source/core/layout/LayoutFieldset.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutFieldset.cpp
@@ -101,7 +101,7 @@
 
         setLogicalLeftForChild(*legend, logicalLeft);
 
-        LayoutUnit fieldsetBorderBefore = borderBefore();
+        LayoutUnit fieldsetBorderBefore = LayoutUnit(borderBefore());
         LayoutUnit legendLogicalHeight = logicalHeightForChild(*legend);
 
         LayoutUnit legendLogicalTop;
diff --git a/third_party/WebKit/Source/core/layout/LayoutFileUploadControl.cpp b/third_party/WebKit/Source/core/layout/LayoutFileUploadControl.cpp
index a4510d4..03dd133 100644
--- a/third_party/WebKit/Source/core/layout/LayoutFileUploadControl.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutFileUploadControl.cpp
@@ -119,13 +119,13 @@
         computeIntrinsicLogicalWidths(m_minPreferredLogicalWidth, m_maxPreferredLogicalWidth);
 
     if (styleToUse.minWidth().isFixed() && styleToUse.minWidth().value() > 0) {
-        m_maxPreferredLogicalWidth = std::max(m_maxPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(styleToUse.minWidth().value()));
-        m_minPreferredLogicalWidth = std::max(m_minPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(styleToUse.minWidth().value()));
+        m_maxPreferredLogicalWidth = std::max(m_maxPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(LayoutUnit(styleToUse.minWidth().value())));
+        m_minPreferredLogicalWidth = std::max(m_minPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(LayoutUnit(styleToUse.minWidth().value())));
     }
 
     if (styleToUse.maxWidth().isFixed()) {
-        m_maxPreferredLogicalWidth = std::min(m_maxPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(styleToUse.maxWidth().value()));
-        m_minPreferredLogicalWidth = std::min(m_minPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(styleToUse.maxWidth().value()));
+        m_maxPreferredLogicalWidth = std::min(m_maxPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(LayoutUnit(styleToUse.maxWidth().value())));
+        m_minPreferredLogicalWidth = std::min(m_minPreferredLogicalWidth, adjustContentBoxLogicalWidthForBoxSizing(LayoutUnit(styleToUse.maxWidth().value())));
     }
 
     int toAdd = borderAndPaddingWidth();
diff --git a/third_party/WebKit/Source/core/layout/LayoutFlexibleBox.cpp b/third_party/WebKit/Source/core/layout/LayoutFlexibleBox.cpp
index 4e0839b..e313279 100644
--- a/third_party/WebKit/Source/core/layout/LayoutFlexibleBox.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutFlexibleBox.cpp
@@ -143,7 +143,7 @@
     minLogicalWidth = std::max(LayoutUnit(), minLogicalWidth);
     maxLogicalWidth = std::max(LayoutUnit(), maxLogicalWidth);
 
-    LayoutUnit scrollbarWidth = intrinsicScrollbarLogicalWidth();
+    LayoutUnit scrollbarWidth(intrinsicScrollbarLogicalWidth());
     maxLogicalWidth += scrollbarWidth;
     minLogicalWidth += scrollbarWidth;
 }
@@ -325,7 +325,7 @@
 
 LayoutUnit LayoutFlexibleBox::clientLogicalBottomAfterRepositioning()
 {
-    LayoutUnit maxChildLogicalBottom = 0;
+    LayoutUnit maxChildLogicalBottom;
     for (LayoutBox* child = firstChildBox(); child; child = child->nextSiblingBox()) {
         if (child->isOutOfFlowPositioned())
             continue;
@@ -491,47 +491,47 @@
 LayoutUnit LayoutFlexibleBox::flowAwareBorderStart() const
 {
     if (isHorizontalFlow())
-        return isLeftToRightFlow() ? borderLeft() : borderRight();
-    return isLeftToRightFlow() ? borderTop() : borderBottom();
+        return LayoutUnit(isLeftToRightFlow() ? borderLeft() : borderRight());
+    return LayoutUnit(isLeftToRightFlow() ? borderTop() : borderBottom());
 }
 
 LayoutUnit LayoutFlexibleBox::flowAwareBorderEnd() const
 {
     if (isHorizontalFlow())
-        return isLeftToRightFlow() ? borderRight() : borderLeft();
-    return isLeftToRightFlow() ? borderBottom() : borderTop();
+        return LayoutUnit(isLeftToRightFlow() ? borderRight() : borderLeft());
+    return LayoutUnit(isLeftToRightFlow() ? borderBottom() : borderTop());
 }
 
 LayoutUnit LayoutFlexibleBox::flowAwareBorderBefore() const
 {
     switch (transformedWritingMode()) {
     case TransformedWritingMode::TopToBottomWritingMode:
-        return borderTop();
+        return LayoutUnit(borderTop());
     case TransformedWritingMode::BottomToTopWritingMode:
-        return borderBottom();
+        return LayoutUnit(borderBottom());
     case TransformedWritingMode::LeftToRightWritingMode:
-        return borderLeft();
+        return LayoutUnit(borderLeft());
     case TransformedWritingMode::RightToLeftWritingMode:
-        return borderRight();
+        return LayoutUnit(borderRight());
     }
     ASSERT_NOT_REACHED();
-    return borderTop();
+    return LayoutUnit(borderTop());
 }
 
 LayoutUnit LayoutFlexibleBox::flowAwareBorderAfter() const
 {
     switch (transformedWritingMode()) {
     case TransformedWritingMode::TopToBottomWritingMode:
-        return borderBottom();
+        return LayoutUnit(borderBottom());
     case TransformedWritingMode::BottomToTopWritingMode:
-        return borderTop();
+        return LayoutUnit(borderTop());
     case TransformedWritingMode::LeftToRightWritingMode:
-        return borderRight();
+        return LayoutUnit(borderRight());
     case TransformedWritingMode::RightToLeftWritingMode:
-        return borderLeft();
+        return LayoutUnit(borderLeft());
     }
     ASSERT_NOT_REACHED();
-    return borderTop();
+    return LayoutUnit(borderTop());
 }
 
 LayoutUnit LayoutFlexibleBox::flowAwarePaddingStart() const
@@ -617,12 +617,12 @@
 
 LayoutUnit LayoutFlexibleBox::crossAxisScrollbarExtent() const
 {
-    return isHorizontalFlow() ? horizontalScrollbarHeight() : verticalScrollbarWidth();
+    return LayoutUnit(isHorizontalFlow() ? horizontalScrollbarHeight() : verticalScrollbarWidth());
 }
 
 LayoutUnit LayoutFlexibleBox::crossAxisScrollbarExtentForChild(const LayoutBox& child) const
 {
-    return isHorizontalFlow() ? child.horizontalScrollbarHeight() : child.verticalScrollbarWidth();
+    return LayoutUnit(isHorizontalFlow() ? child.horizontalScrollbarHeight() : child.verticalScrollbarWidth());
 }
 
 LayoutPoint LayoutFlexibleBox::flowAwareLocationForChild(const LayoutBox& child) const
@@ -653,7 +653,7 @@
 
     LayoutUnit crossSize;
     if (crossSizeLength.isFixed()) {
-        crossSize = crossSizeLength.value();
+        crossSize = LayoutUnit(crossSizeLength.value());
     } else {
         ASSERT(crossSizeLength.hasPercent());
         crossSize = hasOrthogonalFlow(child) ?
@@ -1593,7 +1593,7 @@
             child.setIntrinsicContentLogicalHeight(childIntrinsicContentLogicalHeight);
         }
     } else if (hasOrthogonalFlow(child) && child.style()->logicalWidth().isAuto()) {
-        LayoutUnit childWidth = std::max<LayoutUnit>(0, lineCrossAxisExtent - crossAxisMarginExtentForChild(child));
+        LayoutUnit childWidth = (lineCrossAxisExtent - crossAxisMarginExtentForChild(child)).clampNegativeToZero();
         childWidth = child.constrainLogicalWidthByMinMax(childWidth, childWidth, this);
 
         if (childWidth != child.logicalWidth()) {
diff --git a/third_party/WebKit/Source/core/layout/LayoutGrid.cpp b/third_party/WebKit/Source/core/layout/LayoutGrid.cpp
index 5b7e4f4..1bb89ec2 100644
--- a/third_party/WebKit/Source/core/layout/LayoutGrid.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutGrid.cpp
@@ -455,7 +455,7 @@
         if (m_minContentHeight == -1 || m_maxContentHeight == -1)
             return -1;
         LayoutUnit fillAvailableExtent = containingBlock()->availableLogicalHeight(ExcludeMarginBorderPadding);
-        return std::min<LayoutUnit>(m_maxContentHeight, std::max<LayoutUnit>(m_minContentHeight, fillAvailableExtent));
+        return std::min<LayoutUnit>(m_maxContentHeight, std::max(m_minContentHeight, fillAvailableExtent));
     }
 
     if (logicalHeightLength.isFillAvailable())
@@ -1012,7 +1012,7 @@
         spanningTracksSize += guttersSize(direction, itemSpan.integerSpan());
 
         LayoutUnit extraSpace = currentItemSizeForTrackSizeComputationPhase(phase, gridItemWithSpan.gridItem(), direction, sizingData.columnTracks) - spanningTracksSize;
-        extraSpace = std::max<LayoutUnit>(extraSpace, 0);
+        extraSpace = extraSpace.clampNegativeToZero();
         auto& tracksToGrowBeyondGrowthLimits = sizingData.growBeyondGrowthLimitsTracks.isEmpty() ? sizingData.filteredTracks : sizingData.growBeyondGrowthLimitsTracks;
         distributeSpaceToTracks<phase>(sizingData.filteredTracks, &tracksToGrowBeyondGrowthLimits, sizingData, extraSpace);
     }
@@ -1621,7 +1621,7 @@
     case OverflowAlignmentSafe:
         // If overflow is 'safe', we have to make sure we don't overflow the 'start'
         // edge (potentially cause some data loss as the overflow is unreachable).
-        return std::max<LayoutUnit>(0, offset);
+        return offset.clampNegativeToZero();
     case OverflowAlignmentUnsafe:
     case OverflowAlignmentDefault:
         // If we overflow our alignment container and overflow is 'true' (default), we
diff --git a/third_party/WebKit/Source/core/layout/LayoutInline.cpp b/third_party/WebKit/Source/core/layout/LayoutInline.cpp
index 51843d1..d724d25e 100644
--- a/third_party/WebKit/Source/core/layout/LayoutInline.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutInline.cpp
@@ -243,7 +243,7 @@
     ASSERT_UNUSED(inlineBox, !inlineBox);
 
     if (extraWidthToEndOfLine)
-        *extraWidthToEndOfLine = 0;
+        *extraWidthToEndOfLine = LayoutUnit();
 
     LayoutRect caretRect = localCaretRectForEmptyElement(borderAndPaddingWidth(), 0);
 
@@ -564,10 +564,13 @@
                 RootInlineBox& rootBox = currBox->inlineBoxWrapper()->root();
                 int logicalTop = rootBox.logicalTop() + (rootBox.lineLayoutItem().style(rootBox.isFirstLineStyle())->font().fontMetrics().ascent() - container->style(rootBox.isFirstLineStyle())->font().fontMetrics().ascent());
                 int logicalHeight = container->style(rootBox.isFirstLineStyle())->font().fontMetrics().height();
-                if (isHorizontal)
-                    yield(LayoutRect(currBox->inlineBoxWrapper()->x() - currBox->marginLeft(), logicalTop, currBox->size().width() + currBox->marginWidth(), logicalHeight));
-                else
-                    yield(LayoutRect(logicalTop, currBox->inlineBoxWrapper()->y() - currBox->marginTop(), logicalHeight, currBox->size().height() + currBox->marginHeight()));
+                if (isHorizontal) {
+                    yield(LayoutRect(LayoutUnit(currBox->inlineBoxWrapper()->x() - currBox->marginLeft()), LayoutUnit(logicalTop),
+                        LayoutUnit(currBox->size().width() + currBox->marginWidth()), LayoutUnit(logicalHeight)));
+                } else {
+                    yield(LayoutRect(LayoutUnit(logicalTop), LayoutUnit(currBox->inlineBoxWrapper()->y() - currBox->marginTop()),
+                        LayoutUnit(logicalHeight), currBox->size().height() + currBox->marginHeight()));
+                }
             }
         } else if (curr->isLayoutInline()) {
             // If the child doesn't need line boxes either, then we can recur.
@@ -580,15 +583,15 @@
                     int logicalTop = rootBox.logicalTop() + (rootBox.lineLayoutItem().style(rootBox.isFirstLineStyle())->font().fontMetrics().ascent() - container->style(rootBox.isFirstLineStyle())->font().fontMetrics().ascent());
                     int logicalHeight = container->style(rootBox.isFirstLineStyle())->font().fontMetrics().height();
                     if (isHorizontal) {
-                        yield(LayoutRect(childLine->x() - childLine->marginLogicalLeft(),
-                            logicalTop,
-                            childLine->logicalWidth() + childLine->marginLogicalLeft() + childLine->marginLogicalRight(),
-                            logicalHeight));
+                        yield(LayoutRect(LayoutUnit(childLine->x() - childLine->marginLogicalLeft()),
+                            LayoutUnit(logicalTop),
+                            LayoutUnit(childLine->logicalWidth() + childLine->marginLogicalLeft() + childLine->marginLogicalRight()),
+                            LayoutUnit(logicalHeight)));
                     } else {
-                        yield(LayoutRect(logicalTop,
-                            childLine->y() - childLine->marginLogicalLeft(),
-                            logicalHeight,
-                            childLine->logicalWidth() + childLine->marginLogicalLeft() + childLine->marginLogicalRight()));
+                        yield(LayoutRect(LayoutUnit(logicalTop),
+                            LayoutUnit(childLine->y() - childLine->marginLogicalLeft()),
+                            LayoutUnit(logicalHeight),
+                            LayoutUnit(childLine->logicalWidth() + childLine->marginLogicalLeft() + childLine->marginLogicalRight())));
                     }
                 }
             }
@@ -875,8 +878,8 @@
     ASSERT(!firstLineBox() == !lastLineBox()); // Either both are null or both exist.
     if (firstLineBox() && lastLineBox()) {
         // Return the width of the minimal left side and the maximal right side.
-        LayoutUnit logicalLeftSide = 0;
-        LayoutUnit logicalRightSide = 0;
+        LayoutUnit logicalLeftSide;
+        LayoutUnit logicalRightSide;
         for (InlineFlowBox* curr = firstLineBox(); curr; curr = curr->nextLineBox()) {
             if (curr == firstLineBox() || curr->logicalLeft() < logicalLeftSide)
                 logicalLeftSide = curr->logicalLeft();
diff --git a/third_party/WebKit/Source/core/layout/LayoutInline.h b/third_party/WebKit/Source/core/layout/LayoutInline.h
index fd0d42a..2af191c 100644
--- a/third_party/WebKit/Source/core/layout/LayoutInline.h
+++ b/third_party/WebKit/Source/core/layout/LayoutInline.h
@@ -232,8 +232,8 @@
 
     LayoutUnit offsetLeft() const final;
     LayoutUnit offsetTop() const final;
-    LayoutUnit offsetWidth() const final { return linesBoundingBox().width(); }
-    LayoutUnit offsetHeight() const final { return linesBoundingBox().height(); }
+    LayoutUnit offsetWidth() const final { return LayoutUnit(linesBoundingBox().width()); }
+    LayoutUnit offsetHeight() const final { return LayoutUnit(linesBoundingBox().height()); }
 
     LayoutRect absoluteClippedOverflowRect() const override;
     LayoutRect clippedOverflowRectForPaintInvalidation(const LayoutBoxModelObject* paintInvalidationContainer, const PaintInvalidationState* = nullptr) const override;
diff --git a/third_party/WebKit/Source/core/layout/LayoutListMarker.cpp b/third_party/WebKit/Source/core/layout/LayoutListMarker.cpp
index 1d105b6..644ae0e 100644
--- a/third_party/WebKit/Source/core/layout/LayoutListMarker.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutListMarker.cpp
@@ -447,7 +447,7 @@
         return LayoutRect();
 
     RootInlineBox& root = inlineBoxWrapper()->root();
-    LayoutRect rect(0, root.selectionTop() - location().y(), size().width(), root.selectionHeight());
+    LayoutRect rect(LayoutUnit(), root.selectionTop() - location().y(), size().width(), root.selectionHeight());
     mapToVisibleRectInAncestorSpace(paintInvalidationContainer, rect, nullptr);
     // FIXME: groupedMapping() leaks the squashing abstraction.
     if (paintInvalidationContainer->layer()->groupedMapping())
diff --git a/third_party/WebKit/Source/core/layout/LayoutMultiColumnFlowThread.cpp b/third_party/WebKit/Source/core/layout/LayoutMultiColumnFlowThread.cpp
index 62be3c1a..6130f6f 100644
--- a/third_party/WebKit/Source/core/layout/LayoutMultiColumnFlowThread.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutMultiColumnFlowThread.cpp
@@ -487,7 +487,7 @@
     ASSERT(!columnStyle->hasAutoColumnCount() || !columnStyle->hasAutoColumnWidth());
     if (columnStyle->hasAutoColumnWidth() && !columnStyle->hasAutoColumnCount()) {
         count = computedColumnCount;
-        width = ((availableWidth - ((count - 1) * columnGap)) / count).clampToZero();
+        width = ((availableWidth - ((count - 1) * columnGap)) / count).clampNegativeToZero();
     } else if (!columnStyle->hasAutoColumnWidth() && columnStyle->hasAutoColumnCount()) {
         count = std::max(LayoutUnit(1), (availableWidth + columnGap) / (computedColumnWidth + columnGap));
         width = ((availableWidth + columnGap) / count) - columnGap;
diff --git a/third_party/WebKit/Source/core/layout/LayoutObjectTest.cpp b/third_party/WebKit/Source/core/layout/LayoutObjectTest.cpp
index 330d2954..c62946e 100644
--- a/third_party/WebKit/Source/core/layout/LayoutObjectTest.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutObjectTest.cpp
@@ -116,7 +116,7 @@
     LayoutBlock* container = toLayoutBlock(document().getElementById("container")->layoutObject());
     LayoutText* text = toLayoutText(container->lastChild());
 
-    container->setScrollTop(50);
+    container->setScrollTop(LayoutUnit(50));
     LayoutRect rect(0, 60, 20, 20);
     text->mapToVisibleRectInAncestorSpace(container, rect, nullptr);
     EXPECT_TRUE(rect == LayoutRect(0, 10, 20, 20));
diff --git a/third_party/WebKit/Source/core/layout/LayoutReplaced.cpp b/third_party/WebKit/Source/core/layout/LayoutReplaced.cpp
index 016707b..6c708a0 100644
--- a/third_party/WebKit/Source/core/layout/LayoutReplaced.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutReplaced.cpp
@@ -584,7 +584,7 @@
                 // This solves above equation for 'width' (== logicalWidth).
                 LayoutUnit marginStart = minimumValueForLength(style()->marginStart(), logicalWidth);
                 LayoutUnit marginEnd = minimumValueForLength(style()->marginEnd(), logicalWidth);
-                logicalWidth = std::max<LayoutUnit>(0, logicalWidth - (marginStart + marginEnd + (size().width() - clientWidth())));
+                logicalWidth = (logicalWidth - (marginStart + marginEnd + (size().width() - clientWidth()))).clampNegativeToZero();
                 return computeReplacedLogicalWidthRespectingMinMaxWidth(logicalWidth, shouldComputePreferred);
             }
         }
@@ -730,8 +730,8 @@
     RootInlineBox& root = inlineBoxWrapper()->root();
     LayoutUnit newLogicalTop = root.block().style()->isFlippedBlocksWritingMode() ? inlineBoxWrapper()->logicalBottom() - root.selectionBottom() : root.selectionTop() - inlineBoxWrapper()->logicalTop();
     if (root.block().style()->isHorizontalWritingMode())
-        return LayoutRect(0, newLogicalTop, size().width(), root.selectionHeight());
-    return LayoutRect(newLogicalTop, 0, root.selectionHeight(), size().height());
+        return LayoutRect(LayoutUnit(), newLogicalTop, size().width(), root.selectionHeight());
+    return LayoutRect(newLogicalTop, LayoutUnit(), root.selectionHeight(), size().height());
 }
 
 void LayoutReplaced::setSelectionState(SelectionState state)
diff --git a/third_party/WebKit/Source/core/layout/LayoutSliderContainer.cpp b/third_party/WebKit/Source/core/layout/LayoutSliderContainer.cpp
index 1a4fa83..b117fc1 100644
--- a/third_party/WebKit/Source/core/layout/LayoutSliderContainer.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutSliderContainer.cpp
@@ -69,7 +69,7 @@
 
     if (input->layoutObject()->isSlider() && !isVertical && input->list()) {
         int offsetFromCenter = LayoutTheme::theme().sliderTickOffsetFromTrackCenter();
-        LayoutUnit trackHeight = 0;
+        LayoutUnit trackHeight;
         if (offsetFromCenter < 0) {
             trackHeight = -2 * offsetFromCenter;
         } else {
diff --git a/third_party/WebKit/Source/core/layout/LayoutState.cpp b/third_party/WebKit/Source/core/layout/LayoutState.cpp
index 532fb8e..84546e6 100644
--- a/third_party/WebKit/Source/core/layout/LayoutState.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutState.cpp
@@ -95,7 +95,7 @@
         // writing mode roots.
         if (layoutObject.paginationBreakability() == LayoutBox::ForbidBreaks) {
             m_flowThread = nullptr;
-            m_pageLogicalHeight = 0;
+            m_pageLogicalHeight = LayoutUnit();
             m_isPaginated = false;
         } else {
             m_isPaginated = m_pageLogicalHeight || m_flowThread;
diff --git a/third_party/WebKit/Source/core/layout/LayoutTable.cpp b/third_party/WebKit/Source/core/layout/LayoutTable.cpp
index b0a76c4..1f1e4bf 100644
--- a/third_party/WebKit/Source/core/layout/LayoutTable.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutTable.cpp
@@ -281,7 +281,7 @@
         LayoutUnit marginTotal = marginStart + marginEnd;
 
         // Subtract out our margins to get the available content width.
-        LayoutUnit availableContentLogicalWidth = std::max<LayoutUnit>(0, containerWidthInInlineDirection - marginTotal);
+        LayoutUnit availableContentLogicalWidth = (containerWidthInInlineDirection - marginTotal).clampNegativeToZero();
         if (shrinkToAvoidFloats() && cb->isLayoutBlockFlow() && toLayoutBlockFlow(cb)->containsFloats() && !hasPerpendicularContainingBlock)
             availableContentLogicalWidth = shrinkLogicalWidthToAvoidFloats(marginStart, marginEnd, toLayoutBlockFlow(cb));
 
@@ -356,7 +356,7 @@
     } else {
         ASSERT_NOT_REACHED();
     }
-    return std::max<LayoutUnit>(0, computedLogicalHeight);
+    return computedLogicalHeight.clampNegativeToZero();
 }
 
 void LayoutTable::layoutCaption(LayoutTableCaption& caption)
diff --git a/third_party/WebKit/Source/core/layout/LayoutTable.h b/third_party/WebKit/Source/core/layout/LayoutTable.h
index 529dacd..7ea48f2 100644
--- a/third_party/WebKit/Source/core/layout/LayoutTable.h
+++ b/third_party/WebKit/Source/core/layout/LayoutTable.h
@@ -260,7 +260,7 @@
         if (unsigned effectiveColumnCount = numEffCols())
             return static_cast<LayoutUnit>(effectiveColumnCount + 1) * hBorderSpacing();
 
-        return 0;
+        return LayoutUnit();
     }
 
     // The collapsing border model dissallows paddings on table, which is why we
@@ -272,8 +272,8 @@
     LayoutUnit paddingRight() const override;
 
     // Override paddingStart/End to return pixel values to match behavor of LayoutTableCell.
-    LayoutUnit paddingEnd() const override { return static_cast<int>(LayoutBlock::paddingEnd()); }
-    LayoutUnit paddingStart() const override { return static_cast<int>(LayoutBlock::paddingStart()); }
+    LayoutUnit paddingEnd() const override { return LayoutUnit(static_cast<int>(LayoutBlock::paddingEnd())); }
+    LayoutUnit paddingStart() const override { return LayoutUnit(static_cast<int>(LayoutBlock::paddingStart())); }
 
     LayoutUnit bordersPaddingAndSpacingInRowDirection() const
     {
diff --git a/third_party/WebKit/Source/core/layout/LayoutTableCell.cpp b/third_party/WebKit/Source/core/layout/LayoutTableCell.cpp
index feb7a9c7..89929a6 100644
--- a/third_party/WebKit/Source/core/layout/LayoutTableCell.cpp
+++ b/third_party/WebKit/Source/core/layout/LayoutTableCell.cpp
@@ -238,7 +238,7 @@
     // of them wrong. So if our content's intrinsic height has changed push the new content up into the intrinsic padding and relayout so that the rest of
     // table and row layout can use the correct baseline and height for this cell.
     if (isBaselineAligned() && section()->rowBaseline(rowIndex()) && cellBaselinePosition() > section()->rowBaseline(rowIndex())) {
-        int newIntrinsicPaddingBefore = std::max<LayoutUnit>(0, intrinsicPaddingBefore() - std::max<LayoutUnit>(0, cellBaselinePosition() - oldCellBaseline));
+        int newIntrinsicPaddingBefore = (intrinsicPaddingBefore() - (cellBaselinePosition() - oldCellBaseline).clampNegativeToZero()).clampNegativeToZero();
         setIntrinsicPaddingBefore(newIntrinsicPaddingBefore);
         SubtreeLayoutScope layouter(*this);
         layouter.setNeedsLayout(this, LayoutInvalidationReason::TableChanged);
@@ -297,7 +297,7 @@
 void LayoutTableCell::setOverrideLogicalContentHeightFromRowHeight(LayoutUnit rowHeight)
 {
     clearIntrinsicPadding();
-    setOverrideLogicalContentHeight(std::max<LayoutUnit>(0, rowHeight - borderAndPaddingLogicalHeight()));
+    setOverrideLogicalContentHeight((rowHeight - borderAndPaddingLogicalHeight()).clampNegativeToZero());
 }
 
 LayoutSize LayoutTableCell::offsetFromContainer(const LayoutObject* o, const LayoutPoint& point, bool* offsetDependsOnPoint) const
diff --git a/third_party/WebKit/Source/core/layout/OverflowModelTest.cpp b/third_party/WebKit/Source/core/layout/OverflowModelTest.cpp
index 38ff381..27f0877 100644
--- a/third_party/WebKit/Source/core/layout/OverflowModelTest.cpp
+++ b/third_party/WebKit/Source/core/layout/OverflowModelTest.cpp
@@ -157,20 +157,20 @@
 
 TEST_F(OverflowModelTest, MoveAffectsLayoutOverflow)
 {
-    m_overflow.move(500, 100);
+    m_overflow.move(LayoutUnit(500), LayoutUnit(100));
     EXPECT_EQ(LayoutRect(510, 110, 80, 80), m_overflow.layoutOverflowRect());
 }
 
 TEST_F(OverflowModelTest, MoveAffectsVisualOverflow)
 {
-    m_overflow.move(500, 100);
+    m_overflow.move(LayoutUnit(500), LayoutUnit(100));
     EXPECT_EQ(LayoutRect(500, 100, 100, 100), m_overflow.visualOverflowRect());
 }
 
 TEST_F(OverflowModelTest, MoveAffectsContentsVisualOverflow)
 {
     m_overflow.addContentsVisualOverflow(LayoutRect(0, 0, 10, 10));
-    m_overflow.move(500, 100);
+    m_overflow.move(LayoutUnit(500), LayoutUnit(100));
     EXPECT_EQ(LayoutRect(500, 100, 10, 10), m_overflow.contentsVisualOverflowRect());
 }
 
diff --git a/third_party/WebKit/Source/core/layout/api/LineLayoutBlockFlow.h b/third_party/WebKit/Source/core/layout/api/LineLayoutBlockFlow.h
index 6b221176..685ea77 100644
--- a/third_party/WebKit/Source/core/layout/api/LineLayoutBlockFlow.h
+++ b/third_party/WebKit/Source/core/layout/api/LineLayoutBlockFlow.h
@@ -168,12 +168,12 @@
         return toBlockFlow()->logicalWidthForFloat(floatingObject);
     }
 
-    LayoutUnit logicalRightOffsetForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = 0) const
+    LayoutUnit logicalRightOffsetForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = LayoutUnit()) const
     {
         return toBlockFlow()->logicalRightOffsetForLine(position, indentText, logicalHeight);
     }
 
-    LayoutUnit logicalLeftOffsetForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = 0) const
+    LayoutUnit logicalLeftOffsetForLine(LayoutUnit position, IndentTextOrNot indentText, LayoutUnit logicalHeight = LayoutUnit()) const
     {
         return toBlockFlow()->logicalLeftOffsetForLine(position, indentText, logicalHeight);
     }
diff --git a/third_party/WebKit/Source/core/layout/line/BreakingContextInlineHeaders.h b/third_party/WebKit/Source/core/layout/line/BreakingContextInlineHeaders.h
index 6ba284dd..d8cb265 100644
--- a/third_party/WebKit/Source/core/layout/line/BreakingContextInlineHeaders.h
+++ b/third_party/WebKit/Source/core/layout/line/BreakingContextInlineHeaders.h
@@ -340,7 +340,7 @@
 inline LayoutUnit inlineLogicalWidthFromAncestorsIfNeeded(LineLayoutItem child, bool start = true, bool end = true)
 {
     unsigned lineDepth = 1;
-    LayoutUnit extraWidth = 0;
+    LayoutUnit extraWidth;
     LineLayoutItem parent = child.parent();
     while (parent.isLayoutInline() && lineDepth++ < cMaxLineDepth) {
         LineLayoutInline parentAsLayoutInline(parent);
@@ -532,7 +532,7 @@
 ALWAYS_INLINE float textWidth(LineLayoutText text, unsigned from, unsigned len, const Font& font, float xPos, bool collapseWhiteSpace, HashSet<const SimpleFontData*>* fallbackFonts = nullptr, FloatRect* glyphBounds = nullptr)
 {
     if ((!from && len == text.textLength()) || text.style()->hasTextCombine())
-        return text.width(from, len, font, xPos, text.style()->direction(), fallbackFonts, glyphBounds);
+        return text.width(from, len, font, LayoutUnit(xPos), text.style()->direction(), fallbackFonts, glyphBounds);
 
     TextRun run = constructTextRun(font, text, from, len, text.styleRef());
     run.setTabSize(!collapseWhiteSpace, text.style()->tabSize());
diff --git a/third_party/WebKit/Source/core/layout/line/InlineBox.cpp b/third_party/WebKit/Source/core/layout/line/InlineBox.cpp
index fceffdfd..d07c203 100644
--- a/third_party/WebKit/Source/core/layout/line/InlineBox.cpp
+++ b/third_party/WebKit/Source/core/layout/line/InlineBox.cpp
@@ -150,7 +150,7 @@
     ASSERT(isInlineFlowBox());
     LineLayoutBoxModel flowObject = boxModelObject();
     const FontMetrics& fontMetrics = lineLayoutItem().style(isFirstLineStyle())->fontMetrics();
-    LayoutUnit result = fontMetrics.height();
+    LayoutUnit result(fontMetrics.height());
     if (parent())
         result += flowObject.borderAndPaddingLogicalHeight();
     return result;
@@ -320,7 +320,7 @@
 {
     // Use -1 to mean "we didn't set the position."
     truncatedWidth += logicalWidth();
-    return -1;
+    return LayoutUnit(-1);
 }
 
 void InlineBox::clearKnownToHaveNoOverflow()
diff --git a/third_party/WebKit/Source/core/layout/line/LineInfo.h b/third_party/WebKit/Source/core/layout/line/LineInfo.h
index 7775e85..7487716f 100644
--- a/third_party/WebKit/Source/core/layout/line/LineInfo.h
+++ b/third_party/WebKit/Source/core/layout/line/LineInfo.h
@@ -38,7 +38,6 @@
         , m_isLastLine(false)
         , m_isEmpty(true)
         , m_previousLineBrokeCleanly(true)
-        , m_floatPaginationStrut(0)
         , m_runsFromLeadingWhitespace(0)
     { }
 
@@ -60,7 +59,7 @@
         m_isEmpty = empty;
         if (!empty && block && floatPaginationStrut()) {
             block.setLogicalHeight(block.logicalHeight() + floatPaginationStrut());
-            setFloatPaginationStrut(0);
+            setFloatPaginationStrut(LayoutUnit());
             lineWidth->updateAvailableWidth();
         }
     }
diff --git a/third_party/WebKit/Source/core/layout/line/LineLayoutState.h b/third_party/WebKit/Source/core/layout/line/LineLayoutState.h
index ff9ab4b..ce68b8e 100644
--- a/third_party/WebKit/Source/core/layout/line/LineLayoutState.h
+++ b/third_party/WebKit/Source/core/layout/line/LineLayoutState.h
@@ -45,7 +45,6 @@
         , m_isFullLayout(fullLayout)
         , m_paintInvalidationLogicalTop(paintInvalidationLogicalTop)
         , m_paintInvalidationLogicalBottom(paintInvalidationLogicalBottom)
-        , m_adjustedLogicalLineTop(0)
         , m_usesPaintInvalidationBounds(false)
         , m_flowThread(flowThread)
     { }
@@ -61,11 +60,11 @@
         m_paintInvalidationLogicalTop = m_paintInvalidationLogicalBottom = logicalHeight;
     }
 
-    void updatePaintInvalidationRangeFromBox(RootInlineBox* box, LayoutUnit paginationDelta = 0)
+    void updatePaintInvalidationRangeFromBox(RootInlineBox* box, LayoutUnit paginationDelta = LayoutUnit())
     {
         m_usesPaintInvalidationBounds = true;
-        m_paintInvalidationLogicalTop = std::min(m_paintInvalidationLogicalTop, box->logicalTopVisualOverflow() + std::min<LayoutUnit>(paginationDelta, 0));
-        m_paintInvalidationLogicalBottom = std::max(m_paintInvalidationLogicalBottom, box->logicalBottomVisualOverflow() + std::max<LayoutUnit>(paginationDelta, 0));
+        m_paintInvalidationLogicalTop = std::min(m_paintInvalidationLogicalTop, box->logicalTopVisualOverflow() + paginationDelta.clampPositiveToZero());
+        m_paintInvalidationLogicalBottom = std::max(m_paintInvalidationLogicalBottom, box->logicalBottomVisualOverflow() + paginationDelta.clampNegativeToZero());
     }
 
     bool endLineMatched() const { return m_endLineMatched; }
diff --git a/third_party/WebKit/Source/core/layout/line/LineWidth.h b/third_party/WebKit/Source/core/layout/line/LineWidth.h
index eaa9952..2c9ccb8 100644
--- a/third_party/WebKit/Source/core/layout/line/LineWidth.h
+++ b/third_party/WebKit/Source/core/layout/line/LineWidth.h
@@ -64,7 +64,7 @@
     float availableWidth() const { return m_availableWidth; }
     float trailingWhitespaceWidth() const { return m_trailingWhitespaceWidth; }
 
-    void updateAvailableWidth(LayoutUnit minimumHeight = 0);
+    void updateAvailableWidth(LayoutUnit minimumHeight = LayoutUnit());
     void shrinkAvailableWidthForNewFloatIfNeeded(const FloatingObject&);
     void addUncommittedWidth(float delta) { m_uncommittedWidth += delta; }
     void commit();
diff --git a/third_party/WebKit/Source/core/layout/line/RootInlineBox.cpp b/third_party/WebKit/Source/core/layout/line/RootInlineBox.cpp
index ddfdf35..ee445503 100644
--- a/third_party/WebKit/Source/core/layout/line/RootInlineBox.cpp
+++ b/third_party/WebKit/Source/core/layout/line/RootInlineBox.cpp
@@ -226,7 +226,7 @@
     m_hasAnnotationsBefore = hasAnnotationsBefore;
     m_hasAnnotationsAfter = hasAnnotationsAfter;
 
-    maxHeight = std::max<LayoutUnit>(0, maxHeight);
+    maxHeight = maxHeight.clampNegativeToZero();
 
     setLineTopBottomPositions(lineTop, lineBottom, heightOfBlock, heightOfBlock + maxHeight, selectionBottom);
 
diff --git a/third_party/WebKit/Source/core/layout/line/RootInlineBox.h b/third_party/WebKit/Source/core/layout/line/RootInlineBox.h
index b1c0554..77a8982 100644
--- a/third_party/WebKit/Source/core/layout/line/RootInlineBox.h
+++ b/third_party/WebKit/Source/core/layout/line/RootInlineBox.h
@@ -61,10 +61,10 @@
 
     LayoutUnit selectionTop() const;
     LayoutUnit selectionBottom() const;
-    LayoutUnit selectionHeight() const { return max<LayoutUnit>(0, selectionBottom() - selectionTop()); }
+    LayoutUnit selectionHeight() const { return (selectionBottom() - selectionTop()).clampNegativeToZero(); }
 
     LayoutUnit selectionTopAdjustedForPrecedingBlock() const;
-    LayoutUnit selectionHeightAdjustedForPrecedingBlock() const { return max<LayoutUnit>(0, selectionBottom() - selectionTopAdjustedForPrecedingBlock()); }
+    LayoutUnit selectionHeightAdjustedForPrecedingBlock() const { return (selectionBottom() - selectionTopAdjustedForPrecedingBlock()).clampNegativeToZero(); }
 
     LayoutUnit blockDirectionPointInLine() const;
 
diff --git a/third_party/WebKit/Source/core/layout/shapes/BoxShapeTest.cpp b/third_party/WebKit/Source/core/layout/shapes/BoxShapeTest.cpp
index 2d4f4ed..78c6208 100644
--- a/third_party/WebKit/Source/core/layout/shapes/BoxShapeTest.cpp
+++ b/third_party/WebKit/Source/core/layout/shapes/BoxShapeTest.cpp
@@ -82,15 +82,15 @@
     // Similarly a "line", specified as top,height to the overlap methods,
     // is defined as top <= y < top + height.
 
-    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(-9, 1));
-    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(-10, 0));
-    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(-10, 200));
-    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(5, 10));
-    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(59, 1));
+    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(-9), LayoutUnit(1)));
+    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(-10), LayoutUnit(0)));
+    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(-10), LayoutUnit(200)));
+    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(5), LayoutUnit(10)));
+    EXPECT_TRUE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(59), LayoutUnit(1)));
 
-    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(-12, 2));
-    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(60, 1));
-    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(100, 200));
+    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(-12), LayoutUnit(2)));
+    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(60), LayoutUnit(1)));
+    EXPECT_FALSE(shape->lineOverlapsShapeMarginBounds(LayoutUnit(100), LayoutUnit(200)));
 
     TEST_EXCLUDED_INTERVAL(shape, -9, 1, -10, 110);
     TEST_EXCLUDED_INTERVAL(shape, -10, 0, -10, 110);
diff --git a/third_party/WebKit/Source/core/layout/svg/LayoutSVGForeignObject.cpp b/third_party/WebKit/Source/core/layout/svg/LayoutSVGForeignObject.cpp
index 2d7d09d..5770859 100644
--- a/third_party/WebKit/Source/core/layout/svg/LayoutSVGForeignObject.cpp
+++ b/third_party/WebKit/Source/core/layout/svg/LayoutSVGForeignObject.cpp
@@ -62,7 +62,7 @@
 {
     // FIXME: Investigate in size rounding issues
     // FIXME: Remove unnecessary rounding when layout is off ints: webkit.org/b/63656
-    setWidth(static_cast<int>(roundf(m_viewport.width())));
+    setWidth(LayoutUnit(static_cast<int>(roundf(m_viewport.width()))));
 }
 
 void LayoutSVGForeignObject::computeLogicalHeight(LayoutUnit, LayoutUnit logicalTop, LogicalExtentComputedValues& computedValues) const
@@ -70,7 +70,7 @@
     // FIXME: Investigate in size rounding issues
     // FIXME: Remove unnecessary rounding when layout is off ints: webkit.org/b/63656
     // FIXME: Is this correct for vertical writing mode?
-    computedValues.m_extent = static_cast<int>(roundf(m_viewport.height()));
+    computedValues.m_extent = LayoutUnit(static_cast<int>(roundf(m_viewport.height())));
     computedValues.m_position = logicalTop;
 }
 
diff --git a/third_party/WebKit/Source/core/layout/svg/LayoutSVGInlineText.cpp b/third_party/WebKit/Source/core/layout/svg/LayoutSVGInlineText.cpp
index c9499439..1a6ea6ab 100644
--- a/third_party/WebKit/Source/core/layout/svg/LayoutSVGInlineText.cpp
+++ b/third_party/WebKit/Source/core/layout/svg/LayoutSVGInlineText.cpp
@@ -193,7 +193,7 @@
     if (!closestDistanceFragment)
         return createPositionWithAffinity(0);
 
-    int offset = closestDistanceBox->offsetForPositionInFragment(*closestDistanceFragment, absolutePoint.x() - closestDistancePosition, true);
+    int offset = closestDistanceBox->offsetForPositionInFragment(*closestDistanceFragment, LayoutUnit(absolutePoint.x() - closestDistancePosition), true);
     return createPositionWithAffinity(offset + closestDistanceBox->start(), offset > 0 ? VP_UPSTREAM_IF_POSSIBLE : TextAffinity::Downstream);
 }
 
diff --git a/third_party/WebKit/Source/core/layout/svg/LayoutSVGRoot.cpp b/third_party/WebKit/Source/core/layout/svg/LayoutSVGRoot.cpp
index 708a8dc..b549640 100644
--- a/third_party/WebKit/Source/core/layout/svg/LayoutSVGRoot.cpp
+++ b/third_party/WebKit/Source/core/layout/svg/LayoutSVGRoot.cpp
@@ -50,9 +50,9 @@
 {
     LayoutSize intrinsicSize(calculateIntrinsicSize());
     if (!intrinsicSize.width())
-        intrinsicSize.setWidth(defaultWidth);
+        intrinsicSize.setWidth(LayoutUnit(defaultWidth));
     if (!intrinsicSize.height())
-        intrinsicSize.setHeight(defaultHeight);
+        intrinsicSize.setHeight(LayoutUnit(defaultHeight));
     setIntrinsicSize(intrinsicSize);
 }
 
@@ -117,7 +117,7 @@
 {
     // When we're embedded through SVGImage (border-image/background-image/<html:img>/...) we're forced to resize to a specific size.
     if (!m_containerSize.isEmpty())
-        return m_containerSize.width();
+        return LayoutUnit(m_containerSize.width());
 
     if (isEmbeddedThroughFrameContainingSVGDocument())
         return containingBlock()->availableLogicalWidth();
@@ -129,7 +129,7 @@
 {
     // When we're embedded through SVGImage (border-image/background-image/<html:img>/...) we're forced to resize to a specific size.
     if (!m_containerSize.isEmpty())
-        return m_containerSize.height();
+        return LayoutUnit(m_containerSize.height());
 
     if (isEmbeddedThroughFrameContainingSVGDocument())
         return containingBlock()->availableLogicalHeight(IncludeMarginBorderPadding);
diff --git a/third_party/WebKit/Source/core/page/SpatialNavigation.h b/third_party/WebKit/Source/core/page/SpatialNavigation.h
index b48a382..9c83be6 100644
--- a/third_party/WebKit/Source/core/page/SpatialNavigation.h
+++ b/third_party/WebKit/Source/core/page/SpatialNavigation.h
@@ -138,7 +138,7 @@
 Node* scrollableEnclosingBoxOrParentFrameForNodeInDirection(WebFocusType, Node*);
 LayoutRect nodeRectInAbsoluteCoordinates(Node*, bool ignoreBorder = false);
 LayoutRect frameRectInAbsoluteCoordinates(LocalFrame*);
-LayoutRect virtualRectForDirection(WebFocusType, const LayoutRect& startingRect, LayoutUnit width = 0);
+LayoutRect virtualRectForDirection(WebFocusType, const LayoutRect& startingRect, LayoutUnit width = LayoutUnit());
 LayoutRect virtualRectForAreaElementAndDirection(HTMLAreaElement&, WebFocusType);
 HTMLFrameOwnerElement* frameOwnerElement(FocusCandidate&);
 
diff --git a/third_party/WebKit/Source/core/paint/NinePieceImageGrid.cpp b/third_party/WebKit/Source/core/paint/NinePieceImageGrid.cpp
index 5f0cf28..28e7b0dd 100644
--- a/third_party/WebKit/Source/core/paint/NinePieceImageGrid.cpp
+++ b/third_party/WebKit/Source/core/paint/NinePieceImageGrid.cpp
@@ -12,7 +12,7 @@
 
 namespace blink {
 
-static LayoutUnit computeEdgeWidth(const BorderImageLength& borderSlice, int borderSide, const LayoutUnit& imageSide,
+static int computeEdgeWidth(const BorderImageLength& borderSlice, int borderSide, const LayoutUnit& imageSide,
     const LayoutUnit& boxExtent)
 {
     if (borderSlice.isNumber())
diff --git a/third_party/WebKit/Source/core/paint/PaintInfoTest.cpp b/third_party/WebKit/Source/core/paint/PaintInfoTest.cpp
index 1c9f076e..0ade3a24 100644
--- a/third_party/WebKit/Source/core/paint/PaintInfoTest.cpp
+++ b/third_party/WebKit/Source/core/paint/PaintInfoTest.cpp
@@ -33,7 +33,7 @@
     PaintInfo paintInfo(m_context, IntRect(0, 0, 50, 50), PaintPhaseSelfBlockBackgroundOnly, GlobalPaintNormalPhase, PaintLayerNoFlag);
 
     EXPECT_TRUE(paintInfo.cullRect().intersectsCullRect(LayoutRect(0, 0, 1, 1)));
-    EXPECT_TRUE(paintInfo.cullRect().intersectsCullRect(LayoutRect(0.1, 0.1, 0.1, 0.1)));
+    EXPECT_TRUE(paintInfo.cullRect().intersectsCullRect(LayoutRect(LayoutUnit(0.1), LayoutUnit(0.1), LayoutUnit(0.1), LayoutUnit(0.1))));
 }
 
 TEST_F(PaintInfoTest, intersectsCullRectWithTransform)
@@ -61,16 +61,16 @@
 {
     PaintInfo paintInfo(m_context, IntRect(0, 0, 50, 100), PaintPhaseSelfBlockBackgroundOnly, GlobalPaintNormalPhase, PaintLayerNoFlag);
 
-    EXPECT_TRUE(paintInfo.cullRect().intersectsVerticalRange(0, 1));
-    EXPECT_FALSE(paintInfo.cullRect().intersectsVerticalRange(100, 101));
+    EXPECT_TRUE(paintInfo.cullRect().intersectsVerticalRange(LayoutUnit(0), LayoutUnit(1)));
+    EXPECT_FALSE(paintInfo.cullRect().intersectsVerticalRange(LayoutUnit(100), LayoutUnit(101)));
 }
 
 TEST_F(PaintInfoTest, intersectsHorizontalRange)
 {
     PaintInfo paintInfo(m_context, IntRect(0, 0, 50, 100), PaintPhaseSelfBlockBackgroundOnly, GlobalPaintNormalPhase, PaintLayerNoFlag);
 
-    EXPECT_TRUE(paintInfo.cullRect().intersectsHorizontalRange(0, 1));
-    EXPECT_FALSE(paintInfo.cullRect().intersectsHorizontalRange(50, 51));
+    EXPECT_TRUE(paintInfo.cullRect().intersectsHorizontalRange(LayoutUnit(0), LayoutUnit(1)));
+    EXPECT_FALSE(paintInfo.cullRect().intersectsHorizontalRange(LayoutUnit(50), LayoutUnit(51)));
 }
 
 } // namespace blink
diff --git a/third_party/WebKit/Source/devtools/front_end/bindings/StylesSourceMapping.js b/third_party/WebKit/Source/devtools/front_end/bindings/StylesSourceMapping.js
index 0f1b608..9aeaee65 100644
--- a/third_party/WebKit/Source/devtools/front_end/bindings/StylesSourceMapping.js
+++ b/third_party/WebKit/Source/devtools/front_end/bindings/StylesSourceMapping.js
@@ -47,8 +47,8 @@
     cssModel.target().resourceTreeModel.addEventListener(WebInspector.ResourceTreeModel.EventTypes.MainFrameNavigated, this._unbindAllUISourceCodes, this);
 
     this._cssModel.addEventListener(WebInspector.CSSStyleModel.Events.StyleSheetChanged, this._styleSheetChanged, this);
-    /** @type {!Object.<string, !Map.<string, !Map.<string, !WebInspector.CSSStyleSheetHeader>>>} */
-    this._urlToHeadersByFrameId = {};
+    /** @type {!Map<string, !Map<string, !Map<string, !WebInspector.CSSStyleSheetHeader>>>} */
+    this._urlToHeadersByFrameId = new Map();
     /** @type {!Map.<!WebInspector.UISourceCode, !WebInspector.StyleFile>} */
     this._styleFiles = new Map();
 }
@@ -126,10 +126,10 @@
             return;
 
         WebInspector.cssWorkspaceBinding.pushSourceMapping(header, this);
-        var map = this._urlToHeadersByFrameId[url];
+        var map = this._urlToHeadersByFrameId.get(url);
         if (!map) {
             map = /** @type {!Map.<string, !Map.<string, !WebInspector.CSSStyleSheetHeader>>} */ (new Map());
-            this._urlToHeadersByFrameId[url] = map;
+            this._urlToHeadersByFrameId.set(url, map);
         }
         var headersById = map.get(header.frameId);
         if (!headersById) {
@@ -151,16 +151,16 @@
         if (!url)
             return;
 
-        var map = this._urlToHeadersByFrameId[url];
+        var map = this._urlToHeadersByFrameId.get(url);
         console.assert(map);
         var headersById = map.get(header.frameId);
         console.assert(headersById);
-        headersById.remove(header.id);
+        headersById.delete(header.id);
 
         if (!headersById.size) {
-            map.remove(header.frameId);
+            map.delete(header.frameId);
             if (!map.size) {
-                delete this._urlToHeadersByFrameId[url];
+                this._urlToHeadersByFrameId.delete(url);
                 var uiSourceCode = this._networkMapping.uiSourceCodeForStyleURL(url, header);
                 if (uiSourceCode)
                     this._unbindUISourceCode(uiSourceCode);
@@ -177,7 +177,7 @@
         if (!styleFile)
             return;
         styleFile.dispose();
-        this._styleFiles.remove(uiSourceCode);
+        this._styleFiles.delete(uiSourceCode);
     },
 
     _unbindAllUISourceCodes: function()
@@ -185,7 +185,7 @@
         for (var styleFile of this._styleFiles.keys())
             styleFile.dispose();
         this._styleFiles.clear();
-        this._urlToHeadersByFrameId = {};
+        this._urlToHeadersByFrameId = new Map();
     },
 
     /**
@@ -195,9 +195,9 @@
     {
         var uiSourceCode = /** @type {!WebInspector.UISourceCode} */ (event.data);
         var networkURL = this._networkMapping.networkURL(uiSourceCode);
-        if (!networkURL || !this._urlToHeadersByFrameId[networkURL])
+        if (!networkURL || !this._urlToHeadersByFrameId.has(networkURL))
             return;
-        this._bindUISourceCode(uiSourceCode, this._urlToHeadersByFrameId[networkURL].valuesArray()[0].valuesArray()[0]);
+        this._bindUISourceCode(uiSourceCode, this._urlToHeadersByFrameId.get(networkURL).valuesArray()[0].valuesArray()[0]);
     },
 
     /**
diff --git a/third_party/WebKit/Source/devtools/front_end/sources/TabbedEditorContainer.js b/third_party/WebKit/Source/devtools/front_end/sources/TabbedEditorContainer.js
index 8ae65d1c..75e93ff 100644
--- a/third_party/WebKit/Source/devtools/front_end/sources/TabbedEditorContainer.js
+++ b/third_party/WebKit/Source/devtools/front_end/sources/TabbedEditorContainer.js
@@ -585,18 +585,16 @@
      */
     index: function(url)
     {
-        var index = this._itemsIndex[url];
-        if (typeof index === "number")
-            return index;
-        return -1;
+        return this._itemsIndex.has(url) ? /** @type {number} */(this._itemsIndex.get(url)) : -1;
     },
 
     _rebuildItemIndex: function()
     {
-        this._itemsIndex = {};
+        /** @type {!Map<string, number>} */
+        this._itemsIndex = new Map();
         for (var i = 0; i < this._items.length; ++i) {
-            console.assert(!this._itemsIndex.hasOwnProperty(this._items[i].url));
-            this._itemsIndex[this._items[i].url] = i;
+            console.assert(!this._itemsIndex.has(this._items[i].url));
+            this._itemsIndex.set(this._items[i].url, i);
         }
     },
 
diff --git a/third_party/WebKit/Source/platform/LayoutUnit.h b/third_party/WebKit/Source/platform/LayoutUnit.h
index 6dc5502..ddae437 100644
--- a/third_party/WebKit/Source/platform/LayoutUnit.h
+++ b/third_party/WebKit/Source/platform/LayoutUnit.h
@@ -158,11 +158,16 @@
         return m_value >> kLayoutUnitFractionalBits;
     }
 
-    LayoutUnit clampToZero() const
+    LayoutUnit clampNegativeToZero() const
     {
         return std::max(*this, LayoutUnit());
     }
 
+    LayoutUnit clampPositiveToZero() const
+    {
+        return std::min(*this, LayoutUnit());
+    }
+
     LayoutUnit fraction() const
     {
         // Add the fraction to the size (as opposed to the full location) to avoid overflows.
diff --git a/third_party/WebKit/Source/platform/geometry/LayoutRect.h b/third_party/WebKit/Source/platform/geometry/LayoutRect.h
index f1418a96..c82730de 100644
--- a/third_party/WebKit/Source/platform/geometry/LayoutRect.h
+++ b/third_party/WebKit/Source/platform/geometry/LayoutRect.h
@@ -121,23 +121,23 @@
     {
         LayoutUnit delta = edge - x();
         setX(edge);
-        setWidth((width() - delta).clampToZero());
+        setWidth((width() - delta).clampNegativeToZero());
     }
     void shiftMaxXEdgeTo(LayoutUnit edge)
     {
         LayoutUnit delta = edge - maxX();
-        setWidth((width() + delta).clampToZero());
+        setWidth((width() + delta).clampNegativeToZero());
     }
     void shiftYEdgeTo(LayoutUnit edge)
     {
         LayoutUnit delta = edge - y();
         setY(edge);
-        setHeight((height() - delta).clampToZero());
+        setHeight((height() - delta).clampNegativeToZero());
     }
     void shiftMaxYEdgeTo(LayoutUnit edge)
     {
         LayoutUnit delta = edge - maxY();
-        setHeight((height() + delta).clampToZero());
+        setHeight((height() + delta).clampNegativeToZero());
     }
 
     LayoutPoint minXMinYCorner() const { return m_location; } // typically topLeft
diff --git a/third_party/WebKit/Source/web/WebDevToolsAgentImpl.cpp b/third_party/WebKit/Source/web/WebDevToolsAgentImpl.cpp
index 5813e737..8ceb47c 100644
--- a/third_party/WebKit/Source/web/WebDevToolsAgentImpl.cpp
+++ b/third_party/WebKit/Source/web/WebDevToolsAgentImpl.cpp
@@ -480,12 +480,9 @@
 
     m_pageConsoleAgent->setDebuggerAgent(debuggerAgent->v8DebuggerAgent());
 
-    MainThreadDebugger* mainThreadDebugger = MainThreadDebugger::instance();
     m_injectedScriptManager->injectedScriptHost()->init(
-        debuggerAgent->v8DebuggerAgent(),
         bind<PassRefPtr<TypeBuilder::Runtime::RemoteObject>, PassRefPtr<JSONObject>>(&InspectorInspectorAgent::inspect, m_inspectorAgent.get()),
         bind<>(&InspectorConsoleAgent::clearAllMessages, m_pageConsoleAgent.get()),
-        mainThreadDebugger->debugger(),
         adoptPtr(new PageInjectedScriptHostClient()));
 
     if (m_overlay)
diff --git a/third_party/closure_compiler/externs/passwords_private.js b/third_party/closure_compiler/externs/passwords_private.js
index f138031..10e983b 100644
--- a/third_party/closure_compiler/externs/passwords_private.js
+++ b/third_party/closure_compiler/externs/passwords_private.js
@@ -1,7 +1,14 @@
-// Copyright 2015 The Chromium Authors. All rights reserved.
+// Copyright 2016 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+// This file was generated by:
+//   tools/json_schema_compiler/compiler.py.
+// NOTE: The format of types has changed. 'FooType' is now
+//   'chrome.passwordsPrivate.FooType'.
+// Please run the closure compiler before committing changes.
+// See https://code.google.com/p/chromium/wiki/ClosureCompilation.
+
 /** @fileoverview Externs generated from namespace: passwordsPrivate */
 
 /**
@@ -16,32 +23,32 @@
  * }}
  * @see https://developer.chrome.com/extensions/passwordsPrivate#type-LoginPair
  */
-var LoginPair;
+chrome.passwordsPrivate.LoginPair;
 
 /**
  * @typedef {{
- *   loginPair: LoginPair,
+ *   loginPair: !chrome.passwordsPrivate.LoginPair,
  *   numCharactersInPassword: number,
  *   federationText: (string|undefined)
  * }}
  * @see https://developer.chrome.com/extensions/passwordsPrivate#type-PasswordUiEntry
  */
-var PasswordUiEntry;
+chrome.passwordsPrivate.PasswordUiEntry;
 
 /**
  * @typedef {{
- *   loginPair: LoginPair,
+ *   loginPair: !chrome.passwordsPrivate.LoginPair,
  *   plaintextPassword: string
  * }}
  * @see https://developer.chrome.com/extensions/passwordsPrivate#type-PlaintextPasswordEventParameters
  */
-var PlaintextPasswordEventParameters;
+chrome.passwordsPrivate.PlaintextPasswordEventParameters;
 
 /**
  * Removes the saved password corresponding to |loginPair|. If no saved password
  * for this pair exists, this function is a no-op.
- * @param {LoginPair} loginPair The LoginPair corresponding to the entry to
- *     remove.
+ * @param {!chrome.passwordsPrivate.LoginPair} loginPair The LoginPair
+ *     corresponding to the entry to remove.
  * @see https://developer.chrome.com/extensions/passwordsPrivate#method-removeSavedPassword
  */
 chrome.passwordsPrivate.removeSavedPassword = function(loginPair) {};
@@ -60,8 +67,8 @@
  * some operating systems, this call may result in an OS-level reauthentication.
  * Once the password has been fetched, it will be returned via the
  * onPlaintextPasswordRetrieved event.
- * @param {LoginPair} loginPair The LoginPair corresponding to the entry whose
- *     password     is to be returned.
+ * @param {!chrome.passwordsPrivate.LoginPair} loginPair The LoginPair
+ *     corresponding to the entry whose password     is to be returned.
  * @see https://developer.chrome.com/extensions/passwordsPrivate#method-requestPlaintextPassword
  */
 chrome.passwordsPrivate.requestPlaintextPassword = function(loginPair) {};
diff --git a/third_party/libaddressinput/BUILD.gn b/third_party/libaddressinput/BUILD.gn
index 36fed6f..4132f14 100644
--- a/third_party/libaddressinput/BUILD.gn
+++ b/third_party/libaddressinput/BUILD.gn
@@ -210,8 +210,8 @@
     deps = [
       ":libaddressinput",
       ":strings",
-      "//base:prefs",
       "//base/test:run_all_unittests",
+      "//components/prefs",
       "//net:test_support",
       "//testing/gtest",
     ]
diff --git a/third_party/libaddressinput/libaddressinput.gyp b/third_party/libaddressinput/libaddressinput.gyp
index b9bbbf93..4dc9efb9 100644
--- a/third_party/libaddressinput/libaddressinput.gyp
+++ b/third_party/libaddressinput/libaddressinput.gyp
@@ -110,7 +110,7 @@
       },
       'dependencies': [
         '../../base/base.gyp:base',
-        '../../base/base.gyp:base_prefs',
+        '../../components/prefs/prefs.gyp:prefs',
         '../../net/net.gyp:net',
         '../icu/icu.gyp:icui18n',
         '../icu/icu.gyp:icuuc',
@@ -143,8 +143,8 @@
         'src/cpp/src/',
       ],
       'dependencies': [
-        '../../base/base.gyp:base_prefs',
         '../../base/base.gyp:run_all_unittests',
+        '../../components/prefs/prefs.gyp:prefs',
         '../../net/net.gyp:net_test_support',
         '../../testing/gtest.gyp:gtest',
         'libaddressinput',
diff --git a/tools/clang/scripts/run_tool.py b/tools/clang/scripts/run_tool.py
index a1d29d09..4d9a28a 100755
--- a/tools/clang/scripts/run_tool.py
+++ b/tools/clang/scripts/run_tool.py
@@ -42,6 +42,7 @@
 import functools
 import json
 import multiprocessing
+import os
 import os.path
 import subprocess
 import sys
@@ -316,6 +317,13 @@
       help='optional paths to filter what files the tool is run on')
   args = parser.parse_args()
 
+  os.environ['PATH'] = '%s%s%s' % (
+      os.path.abspath(os.path.join(
+          os.path.dirname(__file__),
+          '../../../third_party/llvm-build/Release+Asserts/bin')),
+      os.pathsep,
+      os.environ['PATH'])
+
   if args.generate_compdb:
     _GenerateCompileDatabase(args.compile_database)
 
diff --git a/ui/base/ime/input_method_auralinux.cc b/ui/base/ime/input_method_auralinux.cc
index 2da8022..0a6c6ff 100644
--- a/ui/base/ime/input_method_auralinux.cc
+++ b/ui/base/ime/input_method_auralinux.cc
@@ -29,7 +29,8 @@
     : text_input_type_(TEXT_INPUT_TYPE_NONE),
       is_sync_mode_(false),
       composition_changed_(false),
-      suppress_next_result_(false) {
+      suppress_next_result_(false),
+      weak_ptr_factory_(this) {
   SetDelegate(delegate);
   context_ =
       LinuxInputMethodContextFactory::instance()->CreateInputMethodContext(
@@ -79,6 +80,37 @@
     }
   }
 
+  // If there's an active IME extension is listening to the key event, and the
+  // current text input client is not password input client, the key event
+  // should be dispatched to the extension engine in the two conditions:
+  // 1) |filtered| == false: the ET_KEY_PRESSED event of non-character key,
+  // or the ET_KEY_RELEASED event of all key.
+  // 2) |filtered| == true && NeedInsertChar(): the ET_KEY_PRESSED event of
+  // character key.
+  if (text_input_type_ != TEXT_INPUT_TYPE_PASSWORD &&
+      GetEngine() && GetEngine()->IsInterestedInKeyEvent() &&
+      (!filtered || NeedInsertChar())) {
+    ui::IMEEngineHandlerInterface::KeyEventDoneCallback callback =
+        base::Bind(&InputMethodAuraLinux::ProcessKeyEventDone,
+                   weak_ptr_factory_.GetWeakPtr(),
+                   base::Owned(new ui::KeyEvent(*event)), filtered);
+    GetEngine()->ProcessKeyEvent(*event, callback);
+  } else {
+    ProcessKeyEventDone(event, filtered, false);
+  }
+}
+
+void InputMethodAuraLinux::ProcessKeyEventDone(ui::KeyEvent* event,
+                                               bool filtered,
+                                               bool is_handled) {
+  DCHECK(event);
+  if (is_handled)
+    return;
+
+  // If the IME extension has not handled the key event, passes the keyevent
+  // back to the previous processing flow. Preconditions for this situation:
+  // 1) |filtered| == false
+  // 2) |filtered| == true && NeedInsertChar()
   ui::EventDispatchDetails details;
   if (event->type() == ui::ET_KEY_PRESSED && filtered) {
     if (NeedInsertChar())
diff --git a/ui/base/ime/input_method_auralinux.h b/ui/base/ime/input_method_auralinux.h
index bdabd7f..7436ceab 100644
--- a/ui/base/ime/input_method_auralinux.h
+++ b/ui/base/ime/input_method_auralinux.h
@@ -57,6 +57,9 @@
   void UpdateContextFocusState();
   void ResetContext();
 
+  // Callback function for IMEEngineHandlerInterface::ProcessKeyEvent.
+  void ProcessKeyEventDone(ui::KeyEvent* event, bool filtered, bool is_handled);
+
   scoped_ptr<LinuxInputMethodContext> context_;
   scoped_ptr<LinuxInputMethodContext> context_simple_;
 
@@ -79,6 +82,9 @@
   // event will be discarded.
   bool suppress_next_result_;
 
+  // Used for making callbacks.
+  base::WeakPtrFactory<InputMethodAuraLinux> weak_ptr_factory_;
+
   DISALLOW_COPY_AND_ASSIGN(InputMethodAuraLinux);
 };